#!/usr/bin/env node
/******/ (() => { // webpackBootstrap
/******/ 	"use strict";
/******/ 	var __webpack_modules__ = ({

/***/ 414:
/***/ ((module, __webpack_exports__, __webpack_require__) => {

/* harmony export */ __webpack_require__.d(__webpack_exports__, {
/* harmony export */   $P: () => (/* binding */ __wbg_new_8a6f238a6ece86ea),
/* harmony export */   $U: () => (/* binding */ __wbg_debug_e17b51583ca6a632),
/* harmony export */   BF: () => (/* binding */ __wbg_setmode_5dc300b865044b65),
/* harmony export */   BZ: () => (/* binding */ __wbindgen_object_clone_ref),
/* harmony export */   CF: () => (/* binding */ __wbg_signal_aaf9ad74119f20a4),
/* harmony export */   Dn: () => (/* binding */ __wbg_next_6574e1a8a62d1055),
/* harmony export */   Ev: () => (/* binding */ __wbg_process_5c1d670bc53614b8),
/* harmony export */   FG: () => (/* binding */ __wbg_getRandomValues_bcb4912f16000dc4),
/* harmony export */   FH: () => (/* binding */ __wbg_buffer_609cc3eee51ed158),
/* harmony export */   FP: () => (/* binding */ __wbg_getwithrefkey_1dc361bd10053bfe),
/* harmony export */   GQ: () => (/* binding */ __wbg_then_44b73946d2fb3e7d),
/* harmony export */   Ge: () => (/* binding */ init_sdk),
/* harmony export */   Gu: () => (/* binding */ __wbindgen_is_string),
/* harmony export */   HB: () => (/* binding */ __wbg_set_65595bdd868b3009),
/* harmony export */   HO: () => (/* binding */ __wbg_msCrypto_0a36e2ec3a343d26),
/* harmony export */   HS: () => (/* binding */ __wbg_has_a5ea9117f258a0ec),
/* harmony export */   Ht: () => (/* binding */ __wbg_newwithlength_a381634e90c276d4),
/* harmony export */   Hz: () => (/* binding */ __wbg_instanceof_Response_f2cc20d9f7dfd644),
/* harmony export */   L1: () => (/* binding */ __wbg_setvariant_d1d41b778dfe9c17),
/* harmony export */   LC: () => (/* binding */ __wbindgen_cb_drop),
/* harmony export */   LM: () => (/* binding */ __wbg_value_cd1ffa7b1ab794f1),
/* harmony export */   Lt: () => (/* binding */ __wbg_require_79b1e9274cde3c87),
/* harmony export */   M2: () => (/* binding */ __wbg_new_78feb108b6472713),
/* harmony export */   Mo: () => (/* binding */ __wbg_headers_9cb51cfd2ac780a4),
/* harmony export */   NJ: () => (/* binding */ __wbg_set_3f1d0b984ed272ed),
/* harmony export */   NN: () => (/* binding */ __wbg_randomFillSync_ab2cfe79ebbf2740),
/* harmony export */   Nh: () => (/* binding */ __wbg_setbody_5923b78a95eedf29),
/* harmony export */   Of: () => (/* binding */ __wbindgen_is_undefined),
/* harmony export */   Ot: () => (/* binding */ __wbg_node_02999533c4ea02e3),
/* harmony export */   Oy: () => (/* binding */ __wbg_String_8f0eb39a4a4c2f66),
/* harmony export */   PP: () => (/* binding */ __wbg_getTime_46267b1c24877e30),
/* harmony export */   PR: () => (/* binding */ __wbindgen_is_function),
/* harmony export */   Py: () => (/* binding */ __wbindgen_memory),
/* harmony export */   QR: () => (/* binding */ __wbindgen_number_new),
/* harmony export */   Qn: () => (/* binding */ __wbindgen_throw),
/* harmony export */   RG: () => (/* binding */ __wbg_new_e25e5aab09ff45db),
/* harmony export */   RK: () => (/* binding */ __wbg_get_b9b93047fe3cf45b),
/* harmony export */   Rj: () => (/* binding */ __wbindgen_error_new),
/* harmony export */   Ry: () => (/* binding */ __wbg_length_e2d2a49132c1b256),
/* harmony export */   SJ: () => (/* binding */ __wbg_instanceof_Uint8Array_17156bcf118086a9),
/* harmony export */   TO: () => (/* binding */ __wbg_subarray_aa9065fa9dc5df96),
/* harmony export */   Tb: () => (/* binding */ __wbg_append_8c7dd8d641a5f01b),
/* harmony export */   Tp: () => (/* binding */ __wbg_url_ae10c34ca209681d),
/* harmony export */   U8: () => (/* binding */ __wbindgen_jsval_loose_eq),
/* harmony export */   Vr: () => (/* binding */ __wbg_newnoargs_105ed471475aaf50),
/* harmony export */   WY: () => (/* binding */ __wbg_error_7534b8e9a36f1ab4),
/* harmony export */   Wq: () => (/* binding */ __wbg_append_b2d1fc16de2a0e81),
/* harmony export */   Xb: () => (/* binding */ __wbg_done_769e5ede4b31c67b),
/* harmony export */   Y6: () => (/* binding */ __wbg_stringify_f7ed6987935b4a24),
/* harmony export */   Yb: () => (/* binding */ __wbg_isSafeInteger_343e2beeeece1bb0),
/* harmony export */   Z8: () => (/* binding */ __wbg_error_80de38b3f7cc3c3c),
/* harmony export */   ZD: () => (/* binding */ __wbg_warn_aaf1f4664a035bd6),
/* harmony export */   _h: () => (/* binding */ __wbg_setmethod_3c5280fe5d890842),
/* harmony export */   _m: () => (/* binding */ __wbg_queueMicrotask_97d92b4fcc8a61c5),
/* harmony export */   a4: () => (/* binding */ __wbg_settype_39ed370d3edd403c),
/* harmony export */   bk: () => (/* binding */ __wbindgen_object_drop_ref),
/* harmony export */   bn: () => (/* binding */ import_ssh_key),
/* harmony export */   c6: () => (/* binding */ __wbg_new_23a2665fac83c611),
/* harmony export */   cR: () => (/* binding */ __wbindgen_closure_wrapper2148),
/* harmony export */   cV: () => (/* binding */ __wbg_append_299d5d48292c0495),
/* harmony export */   d_: () => (/* binding */ __wbg_append_b44785ebeb668479),
/* harmony export */   dz: () => (/* binding */ __wbg_get_67b2ba62fc30de12),
/* harmony export */   eF: () => (/* binding */ __wbindgen_boolean_get),
/* harmony export */   eI: () => (/* binding */ __wbg_length_a446193dc22c12f8),
/* harmony export */   eW: () => (/* binding */ __wbg_iterator_9a24c88df860dc65),
/* harmony export */   fb: () => (/* binding */ __wbg_static_accessor_SELF_37c5d418e4bf5819),
/* harmony export */   g: () => (/* binding */ BitwardenClient),
/* harmony export */   gG: () => (/* binding */ __wbg_instanceof_ArrayBuffer_e14585432e3737fc),
/* harmony export */   gH: () => (/* binding */ __wbg_entries_3265d4158b33e5dc),
/* harmony export */   gM: () => (/* binding */ __wbg_abort_775ef1d17fc65868),
/* harmony export */   gR: () => (/* binding */ __wbg_fetch_509096533071c657),
/* harmony export */   gt: () => (/* binding */ __wbg_text_7805bea50de2af49),
/* harmony export */   hI: () => (/* binding */ __wbg_newwithbyteoffsetandlength_d97e637ebe145a9a),
/* harmony export */   he: () => (/* binding */ __wbg_newwithstrandinit_06c535e0a867c635),
/* harmony export */   i8: () => (/* binding */ __wbg_info_033d8b8a0838f1d3),
/* harmony export */   id: () => (/* binding */ __wbg_new_018dcc2d6c8c2f6a),
/* harmony export */   ii: () => (/* binding */ __wbg_static_accessor_GLOBAL_88a902d13a557d07),
/* harmony export */   il: () => (/* binding */ __wbg_crypto_ed58b8e10a292839),
/* harmony export */   k2: () => (/* binding */ __wbg_queueMicrotask_d3219def82552485),
/* harmony export */   kK: () => (/* binding */ __wbg_status_f6360336ca686bf0),
/* harmony export */   l0: () => (/* binding */ __wbg_setsignal_75b21ef3a81de905),
/* harmony export */   lI: () => (/* binding */ __wbg_set_wasm),
/* harmony export */   o0: () => (/* binding */ __wbg_fetch_4465c2b10f21a927),
/* harmony export */   oo: () => (/* binding */ __wbg_versions_c71aa1626a93e0a1),
/* harmony export */   qN: () => (/* binding */ __wbindgen_string_get),
/* harmony export */   qe: () => (/* binding */ __wbg_newwithu8arraysequenceandoptions_068570c487f69127),
/* harmony export */   qm: () => (/* binding */ __wbindgen_as_number),
/* harmony export */   qv: () => (/* binding */ __wbindgen_is_object),
/* harmony export */   rQ: () => (/* binding */ __wbg_log_cad59bb680daec67),
/* harmony export */   rk: () => (/* binding */ __wbg_setheaders_834c0bdb6a8949ad),
/* harmony export */   rl: () => (/* binding */ __wbindgen_debug_string),
/* harmony export */   sW: () => (/* binding */ __wbindgen_number_get),
/* harmony export */   tT: () => (/* binding */ __wbg_setname_c0e2d6f348c746f4),
/* harmony export */   tZ: () => (/* binding */ __wbg_push_737cfc8c1432c2c6),
/* harmony export */   uw: () => (/* binding */ __wbg_setcredentials_c3a22f1cd105a2c6),
/* harmony export */   v: () => (/* binding */ __wbg_new_405e22f390576ce2),
/* harmony export */   vU: () => (/* binding */ __wbg_new_f24b6d53abe5bc82),
/* harmony export */   vV: () => (/* binding */ __wbg_new_a12002a7f91c75be),
/* harmony export */   w6: () => (/* binding */ __wbg_static_accessor_GLOBAL_THIS_56578be7e9f832b0),
/* harmony export */   w9: () => (/* binding */ __wbg_call_7cccdd69e0791ae2),
/* harmony export */   wH: () => (/* binding */ __wbg_call_672a4d21634d4a24),
/* harmony export */   wJ: () => (/* binding */ __wbg_resolve_4851785c9c5f573d),
/* harmony export */   wd: () => (/* binding */ __wbg_new_c68d7209be747379),
/* harmony export */   x$: () => (/* binding */ __wbg_stack_0ed75d68575b0f3c),
/* harmony export */   x0: () => (/* binding */ __wbg_static_accessor_WINDOW_5de37043a91a9c40),
/* harmony export */   xV: () => (/* binding */ __wbg_then_48b406749878a531),
/* harmony export */   yU: () => (/* binding */ __wbg_new0_f788a2397c7ca929),
/* harmony export */   yc: () => (/* binding */ __wbindgen_string_new),
/* harmony export */   yq: () => (/* binding */ __wbg_next_25feadfc0913fea9),
/* harmony export */   z0: () => (/* binding */ __wbg_new_9fd39a253424609a),
/* harmony export */   zE: () => (/* binding */ __wbindgen_in)
/* harmony export */ });
/* unused harmony exports isEncryptionSettingsError, isCryptoError, isSshKeyExportError, isSshKeyImportError, isKeyGenerationError, isDecryptFileError, isEncryptFileError, isDecryptError, isEncryptError, isTotpError, set_log_level, generate_ssh_key, isTestError, LogLevel, ClientFolders, ClientTotp, CryptoClient, PureCrypto, VaultClient */
/* module decorator */ module = __webpack_require__.hmd(module);
let wasm;
function __wbg_set_wasm(val) {
  wasm = val;
}

const heap = new Array(128).fill(undefined);

heap.push(undefined, null, true, false);

function getObject(idx) {
  return heap[idx];
}

let WASM_VECTOR_LEN = 0;

let cachedUint8ArrayMemory0 = null;

function getUint8ArrayMemory0() {
  if (cachedUint8ArrayMemory0 === null || cachedUint8ArrayMemory0.byteLength === 0) {
    cachedUint8ArrayMemory0 = new Uint8Array(wasm.memory.buffer);
  }
  return cachedUint8ArrayMemory0;
}

const lTextEncoder =
  typeof TextEncoder === "undefined" ? (0, module.require)("util").TextEncoder : TextEncoder;

let cachedTextEncoder = new lTextEncoder("utf-8");

const encodeString =
  typeof cachedTextEncoder.encodeInto === "function"
    ? function (arg, view) {
        return cachedTextEncoder.encodeInto(arg, view);
      }
    : function (arg, view) {
        const buf = cachedTextEncoder.encode(arg);
        view.set(buf);
        return {
          read: arg.length,
          written: buf.length,
        };
      };

function passStringToWasm0(arg, malloc, realloc) {
  if (realloc === undefined) {
    const buf = cachedTextEncoder.encode(arg);
    const ptr = malloc(buf.length, 1) >>> 0;
    getUint8ArrayMemory0()
      .subarray(ptr, ptr + buf.length)
      .set(buf);
    WASM_VECTOR_LEN = buf.length;
    return ptr;
  }

  let len = arg.length;
  let ptr = malloc(len, 1) >>> 0;

  const mem = getUint8ArrayMemory0();

  let offset = 0;

  for (; offset < len; offset++) {
    const code = arg.charCodeAt(offset);
    if (code > 0x7f) break;
    mem[ptr + offset] = code;
  }

  if (offset !== len) {
    if (offset !== 0) {
      arg = arg.slice(offset);
    }
    ptr = realloc(ptr, len, (len = offset + arg.length * 3), 1) >>> 0;
    const view = getUint8ArrayMemory0().subarray(ptr + offset, ptr + len);
    const ret = encodeString(arg, view);

    offset += ret.written;
    ptr = realloc(ptr, len, offset, 1) >>> 0;
  }

  WASM_VECTOR_LEN = offset;
  return ptr;
}

let cachedDataViewMemory0 = null;

function getDataViewMemory0() {
  if (
    cachedDataViewMemory0 === null ||
    cachedDataViewMemory0.buffer.detached === true ||
    (cachedDataViewMemory0.buffer.detached === undefined &&
      cachedDataViewMemory0.buffer !== wasm.memory.buffer)
  ) {
    cachedDataViewMemory0 = new DataView(wasm.memory.buffer);
  }
  return cachedDataViewMemory0;
}

const lTextDecoder =
  typeof TextDecoder === "undefined" ? (0, module.require)("util").TextDecoder : TextDecoder;

let cachedTextDecoder = new lTextDecoder("utf-8", { ignoreBOM: true, fatal: true });

cachedTextDecoder.decode();

function getStringFromWasm0(ptr, len) {
  ptr = ptr >>> 0;
  return cachedTextDecoder.decode(getUint8ArrayMemory0().subarray(ptr, ptr + len));
}

let heap_next = heap.length;

function addHeapObject(obj) {
  if (heap_next === heap.length) heap.push(heap.length + 1);
  const idx = heap_next;
  heap_next = heap[idx];

  heap[idx] = obj;
  return idx;
}

function handleError(f, args) {
  try {
    return f.apply(this, args);
  } catch (e) {
    wasm.__wbindgen_exn_store(addHeapObject(e));
  }
}

function dropObject(idx) {
  if (idx < 132) return;
  heap[idx] = heap_next;
  heap_next = idx;
}

function takeObject(idx) {
  const ret = getObject(idx);
  dropObject(idx);
  return ret;
}

function isLikeNone(x) {
  return x === undefined || x === null;
}

const CLOSURE_DTORS =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((state) => {
        wasm.__wbindgen_export_4.get(state.dtor)(state.a, state.b);
      });

function makeMutClosure(arg0, arg1, dtor, f) {
  const state = { a: arg0, b: arg1, cnt: 1, dtor };
  const real = (...args) => {
    // First up with a closure we increment the internal reference
    // count. This ensures that the Rust closure environment won't
    // be deallocated while we're invoking it.
    state.cnt++;
    const a = state.a;
    state.a = 0;
    try {
      return f(a, state.b, ...args);
    } finally {
      if (--state.cnt === 0) {
        wasm.__wbindgen_export_4.get(state.dtor)(a, state.b);
        CLOSURE_DTORS.unregister(state);
      } else {
        state.a = a;
      }
    }
  };
  real.original = state;
  CLOSURE_DTORS.register(real, state, state);
  return real;
}

function debugString(val) {
  // primitive types
  const type = typeof val;
  if (type == "number" || type == "boolean" || val == null) {
    return `${val}`;
  }
  if (type == "string") {
    return `"${val}"`;
  }
  if (type == "symbol") {
    const description = val.description;
    if (description == null) {
      return "Symbol";
    } else {
      return `Symbol(${description})`;
    }
  }
  if (type == "function") {
    const name = val.name;
    if (typeof name == "string" && name.length > 0) {
      return `Function(${name})`;
    } else {
      return "Function";
    }
  }
  // objects
  if (Array.isArray(val)) {
    const length = val.length;
    let debug = "[";
    if (length > 0) {
      debug += debugString(val[0]);
    }
    for (let i = 1; i < length; i++) {
      debug += ", " + debugString(val[i]);
    }
    debug += "]";
    return debug;
  }
  // Test for built-in
  const builtInMatches = /\[object ([^\]]+)\]/.exec(toString.call(val));
  let className;
  if (builtInMatches && builtInMatches.length > 1) {
    className = builtInMatches[1];
  } else {
    // Failed to match the standard '[object ClassName]'
    return toString.call(val);
  }
  if (className == "Object") {
    // we're a user defined class or Object
    // JSON.stringify avoids problems with cycles, and is generally much
    // easier than looping through ownProperties of `val`.
    try {
      return "Object(" + JSON.stringify(val) + ")";
    } catch (_) {
      return "Object";
    }
  }
  // errors
  if (val instanceof Error) {
    return `${val.name}: ${val.message}\n${val.stack}`;
  }
  // TODO we could test for more things here, like `Set`s and `Map`s.
  return className;
}

let stack_pointer = 128;

function addBorrowedObject(obj) {
  if (stack_pointer == 1) throw new Error("out of js stack");
  heap[--stack_pointer] = obj;
  return stack_pointer;
}
/**
 * @param {any} error
 * @returns {boolean}
 */
function isEncryptionSettingsError(error) {
  try {
    const ret = wasm.isEncryptionSettingsError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isCryptoError(error) {
  try {
    const ret = wasm.isCryptoError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isSshKeyExportError(error) {
  try {
    const ret = wasm.isSshKeyExportError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isSshKeyImportError(error) {
  try {
    const ret = wasm.isSshKeyImportError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isKeyGenerationError(error) {
  try {
    const ret = wasm.isKeyGenerationError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isDecryptFileError(error) {
  try {
    const ret = wasm.isDecryptFileError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isEncryptFileError(error) {
  try {
    const ret = wasm.isEncryptFileError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isDecryptError(error) {
  try {
    const ret = wasm.isDecryptError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isEncryptError(error) {
  try {
    const ret = wasm.isEncryptError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isTotpError(error) {
  try {
    const ret = wasm.isTotpError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

/**
 * @param {LogLevel} level
 */
function set_log_level(level) {
  wasm.set_log_level(level);
}

/**
 * @param {LogLevel | null} [log_level]
 */
function init_sdk(log_level) {
  wasm.init_sdk(isLikeNone(log_level) ? 5 : log_level);
}

function getArrayU8FromWasm0(ptr, len) {
  ptr = ptr >>> 0;
  return getUint8ArrayMemory0().subarray(ptr / 1, ptr / 1 + len);
}

function passArray8ToWasm0(arg, malloc) {
  const ptr = malloc(arg.length * 1, 1) >>> 0;
  getUint8ArrayMemory0().set(arg, ptr / 1);
  WASM_VECTOR_LEN = arg.length;
  return ptr;
}
/**
 * Generate a new SSH key pair
 *
 * # Arguments
 * - `key_algorithm` - The algorithm to use for the key pair
 *
 * # Returns
 * - `Ok(SshKey)` if the key was successfully generated
 * - `Err(KeyGenerationError)` if the key could not be generated
 * @param {KeyAlgorithm} key_algorithm
 * @returns {SshKeyView}
 */
function generate_ssh_key(key_algorithm) {
  try {
    const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
    wasm.generate_ssh_key(retptr, addHeapObject(key_algorithm));
    var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
    var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
    var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
    if (r2) {
      throw takeObject(r1);
    }
    return takeObject(r0);
  } finally {
    wasm.__wbindgen_add_to_stack_pointer(16);
  }
}

/**
 * Convert a PCKS8 or OpenSSH encrypted or unencrypted private key
 * to an OpenSSH private key with public key and fingerprint
 *
 * # Arguments
 * - `imported_key` - The private key to convert
 * - `password` - The password to use for decrypting the key
 *
 * # Returns
 * - `Ok(SshKey)` if the key was successfully coneverted
 * - `Err(PasswordRequired)` if the key is encrypted and no password was provided
 * - `Err(WrongPassword)` if the password provided is incorrect
 * - `Err(ParsingError)` if the key could not be parsed
 * - `Err(UnsupportedKeyType)` if the key type is not supported
 * @param {string} imported_key
 * @param {string | null} [password]
 * @returns {SshKeyView}
 */
function import_ssh_key(imported_key, password) {
  try {
    const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
    const ptr0 = passStringToWasm0(imported_key, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
    const len0 = WASM_VECTOR_LEN;
    var ptr1 = isLikeNone(password)
      ? 0
      : passStringToWasm0(password, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
    var len1 = WASM_VECTOR_LEN;
    wasm.import_ssh_key(retptr, ptr0, len0, ptr1, len1);
    var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
    var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
    var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
    if (r2) {
      throw takeObject(r1);
    }
    return takeObject(r0);
  } finally {
    wasm.__wbindgen_add_to_stack_pointer(16);
  }
}

/**
 * @param {any} error
 * @returns {boolean}
 */
function isTestError(error) {
  try {
    const ret = wasm.isTestError(addBorrowedObject(error));
    return ret !== 0;
  } finally {
    heap[stack_pointer++] = undefined;
  }
}

function __wbg_adapter_40(arg0, arg1, arg2) {
  wasm._dyn_core__ops__function__FnMut__A____Output___R_as_wasm_bindgen__closure__WasmClosure___describe__invoke__h8ef26cc0e999965d(
    arg0,
    arg1,
    addHeapObject(arg2),
  );
}

function __wbg_adapter_150(arg0, arg1, arg2, arg3) {
  wasm.wasm_bindgen__convert__closures__invoke2_mut__h33defb2ea0fdb769(
    arg0,
    arg1,
    addHeapObject(arg2),
    addHeapObject(arg3),
  );
}

/**
 * @enum {0 | 1 | 2 | 3 | 4}
 */
const LogLevel = Object.freeze({
  Trace: 0,
  0: "Trace",
  Debug: 1,
  1: "Debug",
  Info: 2,
  2: "Info",
  Warn: 3,
  3: "Warn",
  Error: 4,
  4: "Error",
});

const __wbindgen_enum_RequestCredentials = ["omit", "same-origin", "include"];

const __wbindgen_enum_RequestMode = ["same-origin", "no-cors", "cors", "navigate"];

const BitwardenClientFinalization =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((ptr) => wasm.__wbg_bitwardenclient_free(ptr >>> 0, 1));

class BitwardenClient {
  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    BitwardenClientFinalization.unregister(this);
    return ptr;
  }

  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_bitwardenclient_free(ptr, 0);
  }
  /**
   * @param {ClientSettings | null} [settings]
   */
  constructor(settings) {
    const ret = wasm.bitwardenclient_new(isLikeNone(settings) ? 0 : addHeapObject(settings));
    this.__wbg_ptr = ret >>> 0;
    BitwardenClientFinalization.register(this, this.__wbg_ptr, this);
    return this;
  }
  /**
   * Test method, echoes back the input
   * @param {string} msg
   * @returns {string}
   */
  echo(msg) {
    let deferred2_0;
    let deferred2_1;
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(msg, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      wasm.bitwardenclient_echo(retptr, this.__wbg_ptr, ptr0, len0);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      deferred2_0 = r0;
      deferred2_1 = r1;
      return getStringFromWasm0(r0, r1);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
      wasm.__wbindgen_free(deferred2_0, deferred2_1, 1);
    }
  }
  /**
   * @returns {string}
   */
  version() {
    let deferred1_0;
    let deferred1_1;
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      wasm.bitwardenclient_version(retptr, this.__wbg_ptr);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      deferred1_0 = r0;
      deferred1_1 = r1;
      return getStringFromWasm0(r0, r1);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
      wasm.__wbindgen_free(deferred1_0, deferred1_1, 1);
    }
  }
  /**
   * @param {string} msg
   */
  throw(msg) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(msg, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      wasm.bitwardenclient_throw(retptr, this.__wbg_ptr, ptr0, len0);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      if (r1) {
        throw takeObject(r0);
      }
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
  /**
   * Test method, calls http endpoint
   * @param {string} url
   * @returns {Promise<string>}
   */
  http_get(url) {
    const ptr0 = passStringToWasm0(url, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
    const len0 = WASM_VECTOR_LEN;
    const ret = wasm.bitwardenclient_http_get(this.__wbg_ptr, ptr0, len0);
    return takeObject(ret);
  }
  /**
   * @returns {CryptoClient}
   */
  crypto() {
    const ret = wasm.bitwardenclient_crypto(this.__wbg_ptr);
    return CryptoClient.__wrap(ret);
  }
  /**
   * @returns {VaultClient}
   */
  vault() {
    const ret = wasm.bitwardenclient_crypto(this.__wbg_ptr);
    return VaultClient.__wrap(ret);
  }
}

const ClientFoldersFinalization =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((ptr) => wasm.__wbg_clientfolders_free(ptr >>> 0, 1));

class ClientFolders {
  static __wrap(ptr) {
    ptr = ptr >>> 0;
    const obj = Object.create(ClientFolders.prototype);
    obj.__wbg_ptr = ptr;
    ClientFoldersFinalization.register(obj, obj.__wbg_ptr, obj);
    return obj;
  }

  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    ClientFoldersFinalization.unregister(this);
    return ptr;
  }

  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_clientfolders_free(ptr, 0);
  }
  /**
   * Decrypt folder
   * @param {Folder} folder
   * @returns {FolderView}
   */
  decrypt(folder) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      wasm.clientfolders_decrypt(retptr, this.__wbg_ptr, addHeapObject(folder));
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      if (r2) {
        throw takeObject(r1);
      }
      return takeObject(r0);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
}

const ClientTotpFinalization =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((ptr) => wasm.__wbg_clienttotp_free(ptr >>> 0, 1));

class ClientTotp {
  static __wrap(ptr) {
    ptr = ptr >>> 0;
    const obj = Object.create(ClientTotp.prototype);
    obj.__wbg_ptr = ptr;
    ClientTotpFinalization.register(obj, obj.__wbg_ptr, obj);
    return obj;
  }

  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    ClientTotpFinalization.unregister(this);
    return ptr;
  }

  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_clienttotp_free(ptr, 0);
  }
  /**
   * Generates a TOTP code from a provided key
   *
   * # Arguments
   * - `key` - Can be:
   *     - A base32 encoded string
   *     - OTP Auth URI
   *     - Steam URI
   * - `time_ms` - Optional timestamp in milliseconds
   *
   * # Returns
   * - `Ok(TotpResponse)` containing the generated code and period
   * - `Err(TotpError)` if code generation fails
   * @param {string} key
   * @param {number | null} [time_ms]
   * @returns {TotpResponse}
   */
  generate_totp(key, time_ms) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(key, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      wasm.clienttotp_generate_totp(
        retptr,
        this.__wbg_ptr,
        ptr0,
        len0,
        !isLikeNone(time_ms),
        isLikeNone(time_ms) ? 0 : time_ms,
      );
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      if (r2) {
        throw takeObject(r1);
      }
      return takeObject(r0);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
}

const CryptoClientFinalization =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((ptr) => wasm.__wbg_cryptoclient_free(ptr >>> 0, 1));

class CryptoClient {
  static __wrap(ptr) {
    ptr = ptr >>> 0;
    const obj = Object.create(CryptoClient.prototype);
    obj.__wbg_ptr = ptr;
    CryptoClientFinalization.register(obj, obj.__wbg_ptr, obj);
    return obj;
  }

  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    CryptoClientFinalization.unregister(this);
    return ptr;
  }

  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_cryptoclient_free(ptr, 0);
  }
  /**
   * Initialization method for the user crypto. Needs to be called before any other crypto
   * operations.
   * @param {InitUserCryptoRequest} req
   * @returns {Promise<void>}
   */
  initialize_user_crypto(req) {
    const ret = wasm.cryptoclient_initialize_user_crypto(this.__wbg_ptr, addHeapObject(req));
    return takeObject(ret);
  }
  /**
   * Initialization method for the organization crypto. Needs to be called after
   * `initialize_user_crypto` but before any other crypto operations.
   * @param {InitOrgCryptoRequest} req
   * @returns {Promise<void>}
   */
  initialize_org_crypto(req) {
    const ret = wasm.cryptoclient_initialize_org_crypto(this.__wbg_ptr, addHeapObject(req));
    return takeObject(ret);
  }
  /**
   * Generates a new key pair and encrypts the private key with the provided user key.
   * Crypto initialization not required.
   * @param {string} user_key
   * @returns {MakeKeyPairResponse}
   */
  make_key_pair(user_key) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(user_key, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      wasm.cryptoclient_make_key_pair(retptr, this.__wbg_ptr, ptr0, len0);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      if (r2) {
        throw takeObject(r1);
      }
      return takeObject(r0);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
  /**
   * Verifies a user's asymmetric keys by decrypting the private key with the provided user
   * key. Returns if the private key is decryptable and if it is a valid matching key.
   * Crypto initialization not required.
   * @param {VerifyAsymmetricKeysRequest} request
   * @returns {VerifyAsymmetricKeysResponse}
   */
  verify_asymmetric_keys(request) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      wasm.cryptoclient_verify_asymmetric_keys(retptr, this.__wbg_ptr, addHeapObject(request));
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      if (r2) {
        throw takeObject(r1);
      }
      return takeObject(r0);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
}

const PureCryptoFinalization =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((ptr) => wasm.__wbg_purecrypto_free(ptr >>> 0, 1));
/**
 * This module represents a stopgap solution to provide access to primitive crypto functions for JS
 * clients. It is not intended to be used outside of the JS clients and this pattern should not be
 * proliferated. It is necessary because we want to use SDK crypto prior to the SDK being fully
 * responsible for state and keys.
 */
class PureCrypto {
  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    PureCryptoFinalization.unregister(this);
    return ptr;
  }

  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_purecrypto_free(ptr, 0);
  }
  /**
   * @param {string} enc_string
   * @param {string} key_b64
   * @returns {string}
   */
  static symmetric_decrypt(enc_string, key_b64) {
    let deferred4_0;
    let deferred4_1;
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(enc_string, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      const ptr1 = passStringToWasm0(key_b64, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len1 = WASM_VECTOR_LEN;
      wasm.purecrypto_symmetric_decrypt(retptr, ptr0, len0, ptr1, len1);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      var r3 = getDataViewMemory0().getInt32(retptr + 4 * 3, true);
      var ptr3 = r0;
      var len3 = r1;
      if (r3) {
        ptr3 = 0;
        len3 = 0;
        throw takeObject(r2);
      }
      deferred4_0 = ptr3;
      deferred4_1 = len3;
      return getStringFromWasm0(ptr3, len3);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
      wasm.__wbindgen_free(deferred4_0, deferred4_1, 1);
    }
  }
  /**
   * @param {string} enc_string
   * @param {string} key_b64
   * @returns {Uint8Array}
   */
  static symmetric_decrypt_to_bytes(enc_string, key_b64) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(enc_string, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      const ptr1 = passStringToWasm0(key_b64, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len1 = WASM_VECTOR_LEN;
      wasm.purecrypto_symmetric_decrypt_to_bytes(retptr, ptr0, len0, ptr1, len1);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      var r3 = getDataViewMemory0().getInt32(retptr + 4 * 3, true);
      if (r3) {
        throw takeObject(r2);
      }
      var v3 = getArrayU8FromWasm0(r0, r1).slice();
      wasm.__wbindgen_free(r0, r1 * 1, 1);
      return v3;
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
  /**
   * @param {Uint8Array} enc_bytes
   * @param {string} key_b64
   * @returns {Uint8Array}
   */
  static symmetric_decrypt_array_buffer(enc_bytes, key_b64) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passArray8ToWasm0(enc_bytes, wasm.__wbindgen_malloc);
      const len0 = WASM_VECTOR_LEN;
      const ptr1 = passStringToWasm0(key_b64, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len1 = WASM_VECTOR_LEN;
      wasm.purecrypto_symmetric_decrypt_array_buffer(retptr, ptr0, len0, ptr1, len1);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      var r3 = getDataViewMemory0().getInt32(retptr + 4 * 3, true);
      if (r3) {
        throw takeObject(r2);
      }
      var v3 = getArrayU8FromWasm0(r0, r1).slice();
      wasm.__wbindgen_free(r0, r1 * 1, 1);
      return v3;
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
  /**
   * @param {string} plain
   * @param {string} key_b64
   * @returns {string}
   */
  static symmetric_encrypt(plain, key_b64) {
    let deferred4_0;
    let deferred4_1;
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passStringToWasm0(plain, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len0 = WASM_VECTOR_LEN;
      const ptr1 = passStringToWasm0(key_b64, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len1 = WASM_VECTOR_LEN;
      wasm.purecrypto_symmetric_encrypt(retptr, ptr0, len0, ptr1, len1);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      var r3 = getDataViewMemory0().getInt32(retptr + 4 * 3, true);
      var ptr3 = r0;
      var len3 = r1;
      if (r3) {
        ptr3 = 0;
        len3 = 0;
        throw takeObject(r2);
      }
      deferred4_0 = ptr3;
      deferred4_1 = len3;
      return getStringFromWasm0(ptr3, len3);
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
      wasm.__wbindgen_free(deferred4_0, deferred4_1, 1);
    }
  }
  /**
   * @param {Uint8Array} plain
   * @param {string} key_b64
   * @returns {Uint8Array}
   */
  static symmetric_encrypt_to_array_buffer(plain, key_b64) {
    try {
      const retptr = wasm.__wbindgen_add_to_stack_pointer(-16);
      const ptr0 = passArray8ToWasm0(plain, wasm.__wbindgen_malloc);
      const len0 = WASM_VECTOR_LEN;
      const ptr1 = passStringToWasm0(key_b64, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
      const len1 = WASM_VECTOR_LEN;
      wasm.purecrypto_symmetric_encrypt_to_array_buffer(retptr, ptr0, len0, ptr1, len1);
      var r0 = getDataViewMemory0().getInt32(retptr + 4 * 0, true);
      var r1 = getDataViewMemory0().getInt32(retptr + 4 * 1, true);
      var r2 = getDataViewMemory0().getInt32(retptr + 4 * 2, true);
      var r3 = getDataViewMemory0().getInt32(retptr + 4 * 3, true);
      if (r3) {
        throw takeObject(r2);
      }
      var v3 = getArrayU8FromWasm0(r0, r1).slice();
      wasm.__wbindgen_free(r0, r1 * 1, 1);
      return v3;
    } finally {
      wasm.__wbindgen_add_to_stack_pointer(16);
    }
  }
}

const VaultClientFinalization =
  typeof FinalizationRegistry === "undefined"
    ? { register: () => {}, unregister: () => {} }
    : new FinalizationRegistry((ptr) => wasm.__wbg_vaultclient_free(ptr >>> 0, 1));

class VaultClient {
  static __wrap(ptr) {
    ptr = ptr >>> 0;
    const obj = Object.create(VaultClient.prototype);
    obj.__wbg_ptr = ptr;
    VaultClientFinalization.register(obj, obj.__wbg_ptr, obj);
    return obj;
  }

  __destroy_into_raw() {
    const ptr = this.__wbg_ptr;
    this.__wbg_ptr = 0;
    VaultClientFinalization.unregister(this);
    return ptr;
  }

  free() {
    const ptr = this.__destroy_into_raw();
    wasm.__wbg_vaultclient_free(ptr, 0);
  }
  /**
   * @returns {ClientFolders}
   */
  folders() {
    const ret = wasm.bitwardenclient_crypto(this.__wbg_ptr);
    return ClientFolders.__wrap(ret);
  }
  /**
   * @returns {ClientTotp}
   */
  totp() {
    const ret = wasm.bitwardenclient_crypto(this.__wbg_ptr);
    return ClientTotp.__wrap(ret);
  }
}

function __wbg_String_8f0eb39a4a4c2f66(arg0, arg1) {
  const ret = String(getObject(arg1));
  const ptr1 = passStringToWasm0(ret, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
  const len1 = WASM_VECTOR_LEN;
  getDataViewMemory0().setInt32(arg0 + 4 * 1, len1, true);
  getDataViewMemory0().setInt32(arg0 + 4 * 0, ptr1, true);
}

function __wbg_abort_775ef1d17fc65868(arg0) {
  getObject(arg0).abort();
}

function __wbg_append_299d5d48292c0495() {
  return handleError(function (arg0, arg1, arg2, arg3, arg4) {
    getObject(arg0).append(getStringFromWasm0(arg1, arg2), getStringFromWasm0(arg3, arg4));
  }, arguments);
}

function __wbg_append_8c7dd8d641a5f01b() {
  return handleError(function (arg0, arg1, arg2, arg3, arg4) {
    getObject(arg0).append(getStringFromWasm0(arg1, arg2), getStringFromWasm0(arg3, arg4));
  }, arguments);
}

function __wbg_append_b2d1fc16de2a0e81() {
  return handleError(function (arg0, arg1, arg2, arg3, arg4, arg5) {
    getObject(arg0).append(
      getStringFromWasm0(arg1, arg2),
      getObject(arg3),
      getStringFromWasm0(arg4, arg5),
    );
  }, arguments);
}

function __wbg_append_b44785ebeb668479() {
  return handleError(function (arg0, arg1, arg2, arg3) {
    getObject(arg0).append(getStringFromWasm0(arg1, arg2), getObject(arg3));
  }, arguments);
}

function __wbg_buffer_609cc3eee51ed158(arg0) {
  const ret = getObject(arg0).buffer;
  return addHeapObject(ret);
}

function __wbg_call_672a4d21634d4a24() {
  return handleError(function (arg0, arg1) {
    const ret = getObject(arg0).call(getObject(arg1));
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_call_7cccdd69e0791ae2() {
  return handleError(function (arg0, arg1, arg2) {
    const ret = getObject(arg0).call(getObject(arg1), getObject(arg2));
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_crypto_ed58b8e10a292839(arg0) {
  const ret = getObject(arg0).crypto;
  return addHeapObject(ret);
}

function __wbg_debug_e17b51583ca6a632(arg0, arg1, arg2, arg3) {
  console.debug(getObject(arg0), getObject(arg1), getObject(arg2), getObject(arg3));
}

function __wbg_done_769e5ede4b31c67b(arg0) {
  const ret = getObject(arg0).done;
  return ret;
}

function __wbg_entries_3265d4158b33e5dc(arg0) {
  const ret = Object.entries(getObject(arg0));
  return addHeapObject(ret);
}

function __wbg_error_7534b8e9a36f1ab4(arg0, arg1) {
  let deferred0_0;
  let deferred0_1;
  try {
    deferred0_0 = arg0;
    deferred0_1 = arg1;
    console.error(getStringFromWasm0(arg0, arg1));
  } finally {
    wasm.__wbindgen_free(deferred0_0, deferred0_1, 1);
  }
}

function __wbg_error_80de38b3f7cc3c3c(arg0, arg1, arg2, arg3) {
  console.error(getObject(arg0), getObject(arg1), getObject(arg2), getObject(arg3));
}

function __wbg_fetch_4465c2b10f21a927(arg0) {
  const ret = fetch(getObject(arg0));
  return addHeapObject(ret);
}

function __wbg_fetch_509096533071c657(arg0, arg1) {
  const ret = getObject(arg0).fetch(getObject(arg1));
  return addHeapObject(ret);
}

function __wbg_getRandomValues_bcb4912f16000dc4() {
  return handleError(function (arg0, arg1) {
    getObject(arg0).getRandomValues(getObject(arg1));
  }, arguments);
}

function __wbg_getTime_46267b1c24877e30(arg0) {
  const ret = getObject(arg0).getTime();
  return ret;
}

function __wbg_get_67b2ba62fc30de12() {
  return handleError(function (arg0, arg1) {
    const ret = Reflect.get(getObject(arg0), getObject(arg1));
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_get_b9b93047fe3cf45b(arg0, arg1) {
  const ret = getObject(arg0)[arg1 >>> 0];
  return addHeapObject(ret);
}

function __wbg_getwithrefkey_1dc361bd10053bfe(arg0, arg1) {
  const ret = getObject(arg0)[getObject(arg1)];
  return addHeapObject(ret);
}

function __wbg_has_a5ea9117f258a0ec() {
  return handleError(function (arg0, arg1) {
    const ret = Reflect.has(getObject(arg0), getObject(arg1));
    return ret;
  }, arguments);
}

function __wbg_headers_9cb51cfd2ac780a4(arg0) {
  const ret = getObject(arg0).headers;
  return addHeapObject(ret);
}

function __wbg_info_033d8b8a0838f1d3(arg0, arg1, arg2, arg3) {
  console.info(getObject(arg0), getObject(arg1), getObject(arg2), getObject(arg3));
}

function __wbg_instanceof_ArrayBuffer_e14585432e3737fc(arg0) {
  let result;
  try {
    result = getObject(arg0) instanceof ArrayBuffer;
  } catch (_) {
    result = false;
  }
  const ret = result;
  return ret;
}

function __wbg_instanceof_Response_f2cc20d9f7dfd644(arg0) {
  let result;
  try {
    result = getObject(arg0) instanceof Response;
  } catch (_) {
    result = false;
  }
  const ret = result;
  return ret;
}

function __wbg_instanceof_Uint8Array_17156bcf118086a9(arg0) {
  let result;
  try {
    result = getObject(arg0) instanceof Uint8Array;
  } catch (_) {
    result = false;
  }
  const ret = result;
  return ret;
}

function __wbg_isSafeInteger_343e2beeeece1bb0(arg0) {
  const ret = Number.isSafeInteger(getObject(arg0));
  return ret;
}

function __wbg_iterator_9a24c88df860dc65() {
  const ret = Symbol.iterator;
  return addHeapObject(ret);
}

function __wbg_length_a446193dc22c12f8(arg0) {
  const ret = getObject(arg0).length;
  return ret;
}

function __wbg_length_e2d2a49132c1b256(arg0) {
  const ret = getObject(arg0).length;
  return ret;
}

function __wbg_log_cad59bb680daec67(arg0, arg1, arg2, arg3) {
  console.log(getObject(arg0), getObject(arg1), getObject(arg2), getObject(arg3));
}

function __wbg_msCrypto_0a36e2ec3a343d26(arg0) {
  const ret = getObject(arg0).msCrypto;
  return addHeapObject(ret);
}

function __wbg_new0_f788a2397c7ca929() {
  const ret = new Date();
  return addHeapObject(ret);
}

function __wbg_new_018dcc2d6c8c2f6a() {
  return handleError(function () {
    const ret = new Headers();
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_new_23a2665fac83c611(arg0, arg1) {
  try {
    var state0 = { a: arg0, b: arg1 };
    var cb0 = (arg0, arg1) => {
      const a = state0.a;
      state0.a = 0;
      try {
        return __wbg_adapter_150(a, state0.b, arg0, arg1);
      } finally {
        state0.a = a;
      }
    };
    const ret = new Promise(cb0);
    return addHeapObject(ret);
  } finally {
    state0.a = state0.b = 0;
  }
}

function __wbg_new_405e22f390576ce2() {
  const ret = new Object();
  return addHeapObject(ret);
}

function __wbg_new_78feb108b6472713() {
  const ret = new Array();
  return addHeapObject(ret);
}

function __wbg_new_8a6f238a6ece86ea() {
  const ret = new Error();
  return addHeapObject(ret);
}

function __wbg_new_9fd39a253424609a() {
  return handleError(function () {
    const ret = new FormData();
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_new_a12002a7f91c75be(arg0) {
  const ret = new Uint8Array(getObject(arg0));
  return addHeapObject(ret);
}

function __wbg_new_c68d7209be747379(arg0, arg1) {
  const ret = new Error(getStringFromWasm0(arg0, arg1));
  return addHeapObject(ret);
}

function __wbg_new_e25e5aab09ff45db() {
  return handleError(function () {
    const ret = new AbortController();
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_new_f24b6d53abe5bc82(arg0, arg1) {
  let deferred0_0;
  let deferred0_1;
  try {
    deferred0_0 = arg0;
    deferred0_1 = arg1;
    const ret = new Error(getStringFromWasm0(arg0, arg1));
    return addHeapObject(ret);
  } finally {
    wasm.__wbindgen_free(deferred0_0, deferred0_1, 1);
  }
}

function __wbg_newnoargs_105ed471475aaf50(arg0, arg1) {
  const ret = new Function(getStringFromWasm0(arg0, arg1));
  return addHeapObject(ret);
}

function __wbg_newwithbyteoffsetandlength_d97e637ebe145a9a(arg0, arg1, arg2) {
  const ret = new Uint8Array(getObject(arg0), arg1 >>> 0, arg2 >>> 0);
  return addHeapObject(ret);
}

function __wbg_newwithlength_a381634e90c276d4(arg0) {
  const ret = new Uint8Array(arg0 >>> 0);
  return addHeapObject(ret);
}

function __wbg_newwithstrandinit_06c535e0a867c635() {
  return handleError(function (arg0, arg1, arg2) {
    const ret = new Request(getStringFromWasm0(arg0, arg1), getObject(arg2));
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_newwithu8arraysequenceandoptions_068570c487f69127() {
  return handleError(function (arg0, arg1) {
    const ret = new Blob(getObject(arg0), getObject(arg1));
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_next_25feadfc0913fea9(arg0) {
  const ret = getObject(arg0).next;
  return addHeapObject(ret);
}

function __wbg_next_6574e1a8a62d1055() {
  return handleError(function (arg0) {
    const ret = getObject(arg0).next();
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_node_02999533c4ea02e3(arg0) {
  const ret = getObject(arg0).node;
  return addHeapObject(ret);
}

function __wbg_process_5c1d670bc53614b8(arg0) {
  const ret = getObject(arg0).process;
  return addHeapObject(ret);
}

function __wbg_push_737cfc8c1432c2c6(arg0, arg1) {
  const ret = getObject(arg0).push(getObject(arg1));
  return ret;
}

function __wbg_queueMicrotask_97d92b4fcc8a61c5(arg0) {
  queueMicrotask(getObject(arg0));
}

function __wbg_queueMicrotask_d3219def82552485(arg0) {
  const ret = getObject(arg0).queueMicrotask;
  return addHeapObject(ret);
}

function __wbg_randomFillSync_ab2cfe79ebbf2740() {
  return handleError(function (arg0, arg1) {
    getObject(arg0).randomFillSync(takeObject(arg1));
  }, arguments);
}

function __wbg_require_79b1e9274cde3c87() {
  return handleError(function () {
    const ret = module.require;
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_resolve_4851785c9c5f573d(arg0) {
  const ret = Promise.resolve(getObject(arg0));
  return addHeapObject(ret);
}

function __wbg_set_3f1d0b984ed272ed(arg0, arg1, arg2) {
  getObject(arg0)[takeObject(arg1)] = takeObject(arg2);
}

function __wbg_set_65595bdd868b3009(arg0, arg1, arg2) {
  getObject(arg0).set(getObject(arg1), arg2 >>> 0);
}

function __wbg_setbody_5923b78a95eedf29(arg0, arg1) {
  getObject(arg0).body = getObject(arg1);
}

function __wbg_setcredentials_c3a22f1cd105a2c6(arg0, arg1) {
  getObject(arg0).credentials = __wbindgen_enum_RequestCredentials[arg1];
}

function __wbg_setheaders_834c0bdb6a8949ad(arg0, arg1) {
  getObject(arg0).headers = getObject(arg1);
}

function __wbg_setmethod_3c5280fe5d890842(arg0, arg1, arg2) {
  getObject(arg0).method = getStringFromWasm0(arg1, arg2);
}

function __wbg_setmode_5dc300b865044b65(arg0, arg1) {
  getObject(arg0).mode = __wbindgen_enum_RequestMode[arg1];
}

function __wbg_setname_c0e2d6f348c746f4(arg0, arg1, arg2) {
  let deferred0_0;
  let deferred0_1;
  try {
    deferred0_0 = arg1;
    deferred0_1 = arg2;
    getObject(arg0).name = getStringFromWasm0(arg1, arg2);
  } finally {
    wasm.__wbindgen_free(deferred0_0, deferred0_1, 1);
  }
}

function __wbg_setsignal_75b21ef3a81de905(arg0, arg1) {
  getObject(arg0).signal = getObject(arg1);
}

function __wbg_settype_39ed370d3edd403c(arg0, arg1, arg2) {
  getObject(arg0).type = getStringFromWasm0(arg1, arg2);
}

function __wbg_setvariant_d1d41b778dfe9c17(arg0, arg1, arg2) {
  let deferred0_0;
  let deferred0_1;
  try {
    deferred0_0 = arg1;
    deferred0_1 = arg2;
    getObject(arg0).variant = getStringFromWasm0(arg1, arg2);
  } finally {
    wasm.__wbindgen_free(deferred0_0, deferred0_1, 1);
  }
}

function __wbg_signal_aaf9ad74119f20a4(arg0) {
  const ret = getObject(arg0).signal;
  return addHeapObject(ret);
}

function __wbg_stack_0ed75d68575b0f3c(arg0, arg1) {
  const ret = getObject(arg1).stack;
  const ptr1 = passStringToWasm0(ret, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
  const len1 = WASM_VECTOR_LEN;
  getDataViewMemory0().setInt32(arg0 + 4 * 1, len1, true);
  getDataViewMemory0().setInt32(arg0 + 4 * 0, ptr1, true);
}

function __wbg_static_accessor_GLOBAL_88a902d13a557d07() {
  const ret = typeof global === "undefined" ? null : global;
  return isLikeNone(ret) ? 0 : addHeapObject(ret);
}

function __wbg_static_accessor_GLOBAL_THIS_56578be7e9f832b0() {
  const ret = typeof globalThis === "undefined" ? null : globalThis;
  return isLikeNone(ret) ? 0 : addHeapObject(ret);
}

function __wbg_static_accessor_SELF_37c5d418e4bf5819() {
  const ret = typeof self === "undefined" ? null : self;
  return isLikeNone(ret) ? 0 : addHeapObject(ret);
}

function __wbg_static_accessor_WINDOW_5de37043a91a9c40() {
  const ret = typeof window === "undefined" ? null : window;
  return isLikeNone(ret) ? 0 : addHeapObject(ret);
}

function __wbg_status_f6360336ca686bf0(arg0) {
  const ret = getObject(arg0).status;
  return ret;
}

function __wbg_stringify_f7ed6987935b4a24() {
  return handleError(function (arg0) {
    const ret = JSON.stringify(getObject(arg0));
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_subarray_aa9065fa9dc5df96(arg0, arg1, arg2) {
  const ret = getObject(arg0).subarray(arg1 >>> 0, arg2 >>> 0);
  return addHeapObject(ret);
}

function __wbg_text_7805bea50de2af49() {
  return handleError(function (arg0) {
    const ret = getObject(arg0).text();
    return addHeapObject(ret);
  }, arguments);
}

function __wbg_then_44b73946d2fb3e7d(arg0, arg1) {
  const ret = getObject(arg0).then(getObject(arg1));
  return addHeapObject(ret);
}

function __wbg_then_48b406749878a531(arg0, arg1, arg2) {
  const ret = getObject(arg0).then(getObject(arg1), getObject(arg2));
  return addHeapObject(ret);
}

function __wbg_url_ae10c34ca209681d(arg0, arg1) {
  const ret = getObject(arg1).url;
  const ptr1 = passStringToWasm0(ret, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
  const len1 = WASM_VECTOR_LEN;
  getDataViewMemory0().setInt32(arg0 + 4 * 1, len1, true);
  getDataViewMemory0().setInt32(arg0 + 4 * 0, ptr1, true);
}

function __wbg_value_cd1ffa7b1ab794f1(arg0) {
  const ret = getObject(arg0).value;
  return addHeapObject(ret);
}

function __wbg_versions_c71aa1626a93e0a1(arg0) {
  const ret = getObject(arg0).versions;
  return addHeapObject(ret);
}

function __wbg_warn_aaf1f4664a035bd6(arg0, arg1, arg2, arg3) {
  console.warn(getObject(arg0), getObject(arg1), getObject(arg2), getObject(arg3));
}

function __wbindgen_as_number(arg0) {
  const ret = +getObject(arg0);
  return ret;
}

function __wbindgen_boolean_get(arg0) {
  const v = getObject(arg0);
  const ret = typeof v === "boolean" ? (v ? 1 : 0) : 2;
  return ret;
}

function __wbindgen_cb_drop(arg0) {
  const obj = takeObject(arg0).original;
  if (obj.cnt-- == 1) {
    obj.a = 0;
    return true;
  }
  const ret = false;
  return ret;
}

function __wbindgen_closure_wrapper2148(arg0, arg1, arg2) {
  const ret = makeMutClosure(arg0, arg1, 548, __wbg_adapter_40);
  return addHeapObject(ret);
}

function __wbindgen_debug_string(arg0, arg1) {
  const ret = debugString(getObject(arg1));
  const ptr1 = passStringToWasm0(ret, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
  const len1 = WASM_VECTOR_LEN;
  getDataViewMemory0().setInt32(arg0 + 4 * 1, len1, true);
  getDataViewMemory0().setInt32(arg0 + 4 * 0, ptr1, true);
}

function __wbindgen_error_new(arg0, arg1) {
  const ret = new Error(getStringFromWasm0(arg0, arg1));
  return addHeapObject(ret);
}

function __wbindgen_in(arg0, arg1) {
  const ret = getObject(arg0) in getObject(arg1);
  return ret;
}

function __wbindgen_is_function(arg0) {
  const ret = typeof getObject(arg0) === "function";
  return ret;
}

function __wbindgen_is_object(arg0) {
  const val = getObject(arg0);
  const ret = typeof val === "object" && val !== null;
  return ret;
}

function __wbindgen_is_string(arg0) {
  const ret = typeof getObject(arg0) === "string";
  return ret;
}

function __wbindgen_is_undefined(arg0) {
  const ret = getObject(arg0) === undefined;
  return ret;
}

function __wbindgen_jsval_loose_eq(arg0, arg1) {
  const ret = getObject(arg0) == getObject(arg1);
  return ret;
}

function __wbindgen_memory() {
  const ret = wasm.memory;
  return addHeapObject(ret);
}

function __wbindgen_number_get(arg0, arg1) {
  const obj = getObject(arg1);
  const ret = typeof obj === "number" ? obj : undefined;
  getDataViewMemory0().setFloat64(arg0 + 8 * 1, isLikeNone(ret) ? 0 : ret, true);
  getDataViewMemory0().setInt32(arg0 + 4 * 0, !isLikeNone(ret), true);
}

function __wbindgen_number_new(arg0) {
  const ret = arg0;
  return addHeapObject(ret);
}

function __wbindgen_object_clone_ref(arg0) {
  const ret = getObject(arg0);
  return addHeapObject(ret);
}

function __wbindgen_object_drop_ref(arg0) {
  takeObject(arg0);
}

function __wbindgen_string_get(arg0, arg1) {
  const obj = getObject(arg1);
  const ret = typeof obj === "string" ? obj : undefined;
  var ptr1 = isLikeNone(ret)
    ? 0
    : passStringToWasm0(ret, wasm.__wbindgen_malloc, wasm.__wbindgen_realloc);
  var len1 = WASM_VECTOR_LEN;
  getDataViewMemory0().setInt32(arg0 + 4 * 1, len1, true);
  getDataViewMemory0().setInt32(arg0 + 4 * 0, ptr1, true);
}

function __wbindgen_string_new(arg0, arg1) {
  const ret = getStringFromWasm0(arg0, arg1);
  return addHeapObject(ret);
}

function __wbindgen_throw(arg0, arg1) {
  throw new Error(getStringFromWasm0(arg0, arg1));
}


/***/ }),

/***/ 329:
/***/ ((module) => {

module.exports = require("argon2");

/***/ }),

/***/ 80:
/***/ ((module) => {

module.exports = require("open");

/***/ }),

/***/ 857:
/***/ ((module) => {

module.exports = require("url");

/***/ }),

/***/ 330:
/***/ ((module) => {

module.exports = /*#__PURE__*/JSON.parse('{"name":"@bitwarden/cli","description":"A secure and free password manager for all of your devices.","version":"2025.3.0","keywords":["bitwarden","password","vault","password manager","cli"],"author":"Bitwarden Inc. <hello@bitwarden.com> (https://bitwarden.com)","homepage":"https://bitwarden.com","repository":{"type":"git","url":"https://github.com/bitwarden/clients"},"license":"SEE LICENSE IN LICENSE.txt","scripts":{"clean":"rimraf dist","build:oss":"cross-env NODE_OPTIONS=\\"--max-old-space-size=8192\\" webpack","build:oss:debug":"npm run build:oss && node --inspect ./build/bw.js","build:oss:watch":"webpack --watch","build:oss:prod":"cross-env NODE_ENV=production webpack","build:oss:prod:watch":"cross-env NODE_ENV=production webpack --watch","debug":"node --inspect ./build/bw.js","publish:npm":"npm run build:oss:prod && npm publish --access public","build:bit":"cross-env NODE_OPTIONS=\\"--max-old-space-size=8192\\" webpack -c ../../bitwarden_license/bit-cli/webpack.config.js","build:bit:debug":"npm run build:bit && node --inspect ./build/bw.js","build:bit:watch":"webpack --watch -c ../../bitwarden_license/bit-cli/webpack.config.js","build:bit:prod":"cross-env NODE_ENV=production npm run build:bit","build:bit:prod:watch":"cross-env NODE_ENV=production npm run build:bit:watch","dist:oss:win":"npm run build:oss:prod && npm run clean && npm run package:oss:win","dist:oss:mac":"npm run build:oss:prod && npm run clean && npm run package:oss:mac","dist:oss:mac-arm64":"npm run build:oss:prod && npm run clean && npm run package:oss:mac-arm64","dist:oss:lin":"npm run build:oss:prod && npm run clean && npm run package:oss:lin","dist:bit:win":"npm run build:bit:prod && npm run clean && npm run package:bit:win","dist:bit:mac":"npm run build:bit:prod && npm run clean && npm run package:bit:mac","dist:bit:mac-arm64":"npm run build:bit:prod && npm run clean && npm run package:bit:mac-arm64","dist:bit:lin":"npm run build:bit:prod && npm run clean && npm run package:bit:lin","package:oss:win":"pkg . --targets win-x64 --output ./dist/oss/windows/bw.exe","package:oss:mac":"pkg . --targets macos-x64 --output ./dist/oss/macos/bw","package:oss:mac-arm64":"pkg . --targets macos-arm64 --output ./dist/oss/macos-arm64/bw","package:oss:lin":"pkg . --targets linux-x64 --output ./dist/oss/linux/bw","package:bit:win":"pkg . --targets win-x64 --output ./dist/bit/windows/bw.exe","package:bit:mac":"pkg . --targets macos-x64 --output ./dist/bit/macos/bw","package:bit:mac-arm64":"pkg . --targets macos-arm64 --output ./dist/bit/macos-arm64/bw","package:bit:lin":"pkg . --targets linux-x64 --output ./dist/bit/linux/bw","test":"jest","test:watch":"jest --watch","test:watch:all":"jest --watchAll"},"bin":{"bw":"build/bw.js"},"pkg":{"assets":["./build/**/*","../../node_modules/argon2/**/*"]},"dependencies":{"@koa/multer":"3.0.2","@koa/router":"13.1.0","argon2":"0.41.1","big-integer":"1.6.52","browser-hrtime":"1.1.8","chalk":"4.1.2","commander":"11.1.0","form-data":"4.0.1","https-proxy-agent":"7.0.6","inquirer":"8.2.6","jsdom":"26.0.0","jszip":"3.10.1","koa":"2.15.4","koa-bodyparser":"4.4.1","koa-json":"2.0.2","lowdb":"1.0.0","lunr":"2.3.9","multer":"1.4.5-lts.1","node-fetch":"2.6.12","node-forge":"1.3.1","open":"8.4.2","papaparse":"5.5.2","proper-lockfile":"4.1.2","rxjs":"7.8.1","tldts":"6.1.77","zxcvbn":"4.4.2"}}');

/***/ })

/******/ 	});
/************************************************************************/
/******/ 	// The module cache
/******/ 	var __webpack_module_cache__ = {};
/******/ 	
/******/ 	// The require function
/******/ 	function __webpack_require__(moduleId) {
/******/ 		// Check if module is in cache
/******/ 		var cachedModule = __webpack_module_cache__[moduleId];
/******/ 		if (cachedModule !== undefined) {
/******/ 			return cachedModule.exports;
/******/ 		}
/******/ 		// Create a new module (and put it into the cache)
/******/ 		var module = __webpack_module_cache__[moduleId] = {
/******/ 			id: moduleId,
/******/ 			loaded: false,
/******/ 			exports: {}
/******/ 		};
/******/ 	
/******/ 		// Execute the module function
/******/ 		__webpack_modules__[moduleId](module, module.exports, __webpack_require__);
/******/ 	
/******/ 		// Flag the module as loaded
/******/ 		module.loaded = true;
/******/ 	
/******/ 		// Return the exports of the module
/******/ 		return module.exports;
/******/ 	}
/******/ 	
/******/ 	// expose the modules object (__webpack_modules__)
/******/ 	__webpack_require__.m = __webpack_modules__;
/******/ 	
/************************************************************************/
/******/ 	/* webpack/runtime/compat get default export */
/******/ 	(() => {
/******/ 		// getDefaultExport function for compatibility with non-harmony modules
/******/ 		__webpack_require__.n = (module) => {
/******/ 			var getter = module && module.__esModule ?
/******/ 				() => (module['default']) :
/******/ 				() => (module);
/******/ 			__webpack_require__.d(getter, { a: getter });
/******/ 			return getter;
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/create fake namespace object */
/******/ 	(() => {
/******/ 		var getProto = Object.getPrototypeOf ? (obj) => (Object.getPrototypeOf(obj)) : (obj) => (obj.__proto__);
/******/ 		var leafPrototypes;
/******/ 		// create a fake namespace object
/******/ 		// mode & 1: value is a module id, require it
/******/ 		// mode & 2: merge all properties of value into the ns
/******/ 		// mode & 4: return value when already ns object
/******/ 		// mode & 16: return value when it's Promise-like
/******/ 		// mode & 8|1: behave like require
/******/ 		__webpack_require__.t = function(value, mode) {
/******/ 			if(mode & 1) value = this(value);
/******/ 			if(mode & 8) return value;
/******/ 			if(typeof value === 'object' && value) {
/******/ 				if((mode & 4) && value.__esModule) return value;
/******/ 				if((mode & 16) && typeof value.then === 'function') return value;
/******/ 			}
/******/ 			var ns = Object.create(null);
/******/ 			__webpack_require__.r(ns);
/******/ 			var def = {};
/******/ 			leafPrototypes = leafPrototypes || [null, getProto({}), getProto([]), getProto(getProto)];
/******/ 			for(var current = mode & 2 && value; typeof current == 'object' && !~leafPrototypes.indexOf(current); current = getProto(current)) {
/******/ 				Object.getOwnPropertyNames(current).forEach((key) => (def[key] = () => (value[key])));
/******/ 			}
/******/ 			def['default'] = () => (value);
/******/ 			__webpack_require__.d(ns, def);
/******/ 			return ns;
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/define property getters */
/******/ 	(() => {
/******/ 		// define getter functions for harmony exports
/******/ 		__webpack_require__.d = (exports, definition) => {
/******/ 			for(var key in definition) {
/******/ 				if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {
/******/ 					Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });
/******/ 				}
/******/ 			}
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/ensure chunk */
/******/ 	(() => {
/******/ 		__webpack_require__.f = {};
/******/ 		// This file contains only the entry chunk.
/******/ 		// The chunk loading function for additional chunks
/******/ 		__webpack_require__.e = (chunkId) => {
/******/ 			return Promise.all(Object.keys(__webpack_require__.f).reduce((promises, key) => {
/******/ 				__webpack_require__.f[key](chunkId, promises);
/******/ 				return promises;
/******/ 			}, []));
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/get javascript chunk filename */
/******/ 	(() => {
/******/ 		// This function allow to reference async chunks
/******/ 		__webpack_require__.u = (chunkId) => {
/******/ 			// return url for filenames based on template
/******/ 			return "" + chunkId + ".js";
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/harmony module decorator */
/******/ 	(() => {
/******/ 		__webpack_require__.hmd = (module) => {
/******/ 			module = Object.create(module);
/******/ 			if (!module.children) module.children = [];
/******/ 			Object.defineProperty(module, 'exports', {
/******/ 				enumerable: true,
/******/ 				set: () => {
/******/ 					throw new Error('ES Modules may not assign module.exports or exports.*, Use ESM export syntax, instead: ' + module.id);
/******/ 				}
/******/ 			});
/******/ 			return module;
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/hasOwnProperty shorthand */
/******/ 	(() => {
/******/ 		__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/make namespace object */
/******/ 	(() => {
/******/ 		// define __esModule on exports
/******/ 		__webpack_require__.r = (exports) => {
/******/ 			if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
/******/ 				Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
/******/ 			}
/******/ 			Object.defineProperty(exports, '__esModule', { value: true });
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/wasm loading */
/******/ 	(() => {
/******/ 		__webpack_require__.v = (exports, wasmModuleId, wasmModuleHash, importsObj) => {
/******/ 		
/******/ 			return new Promise(function (resolve, reject) {
/******/ 				try {
/******/ 					var { readFile } = require('fs');
/******/ 					var { join } = require('path');
/******/ 		
/******/ 					readFile(join(__dirname, "" + wasmModuleHash + ".module.wasm"), function(err, buffer){
/******/ 						if (err) return reject(err);
/******/ 		
/******/ 						// Fake fetch response
/******/ 						resolve({
/******/ 							arrayBuffer() { return buffer; }
/******/ 						});
/******/ 					});
/******/ 				} catch (err) { reject(err); }
/******/ 			})
/******/ 				.then((x) => (x.arrayBuffer()))
/******/ 				.then((bytes) => (WebAssembly.instantiate(bytes, importsObj)))
/******/ 				.then((res) => (Object.assign(exports, res.instance.exports)));
/******/ 		};
/******/ 	})();
/******/ 	
/******/ 	/* webpack/runtime/require chunk loading */
/******/ 	(() => {
/******/ 		// no baseURI
/******/ 		
/******/ 		// object to store loaded chunks
/******/ 		// "1" means "loaded", otherwise not loaded yet
/******/ 		var installedChunks = {
/******/ 			570: 1
/******/ 		};
/******/ 		
/******/ 		// no on chunks loaded
/******/ 		
/******/ 		var installChunk = (chunk) => {
/******/ 			var moreModules = chunk.modules, chunkIds = chunk.ids, runtime = chunk.runtime;
/******/ 			for(var moduleId in moreModules) {
/******/ 				if(__webpack_require__.o(moreModules, moduleId)) {
/******/ 					__webpack_require__.m[moduleId] = moreModules[moduleId];
/******/ 				}
/******/ 			}
/******/ 			if(runtime) runtime(__webpack_require__);
/******/ 			for(var i = 0; i < chunkIds.length; i++)
/******/ 				installedChunks[chunkIds[i]] = 1;
/******/ 		
/******/ 		};
/******/ 		
/******/ 		// require() chunk loading for javascript
/******/ 		__webpack_require__.f.require = (chunkId, promises) => {
/******/ 			// "1" is the signal for "already loaded"
/******/ 			if(!installedChunks[chunkId]) {
/******/ 				if(true) { // all chunks have JS
/******/ 					installChunk(require("./" + __webpack_require__.u(chunkId)));
/******/ 				} else installedChunks[chunkId] = 1;
/******/ 			}
/******/ 		};
/******/ 		
/******/ 		// no external install chunk
/******/ 		
/******/ 		// no HMR
/******/ 		
/******/ 		// no HMR manifest
/******/ 	})();
/******/ 	
/************************************************************************/
var __webpack_exports__ = {};

// NAMESPACE OBJECT: ../../libs/tools/generator/core/src/engine/index.ts
var bw_engine_namespaceObject = {};
__webpack_require__.r(bw_engine_namespaceObject);
__webpack_require__.d(bw_engine_namespaceObject, {
  Lq: () => (bw_EmailCalculator),
  Mt: () => (bw_EmailRandomizer),
  sF: () => (bw_forwarder_context_ForwarderContext),
  q4: () => (bw_key_service_randomizer_KeyServiceRandomizer),
  Zx: () => (bw_PasswordRandomizer),
  QS: () => (bw_UsernameRandomizer)
});

// NAMESPACE OBJECT: ../../libs/tools/generator/core/src/strategies/index.ts
var bw_strategies_namespaceObject = {};
__webpack_require__.r(bw_strategies_namespaceObject);
__webpack_require__.d(bw_strategies_namespaceObject, {
  B: () => (bw_CatchallGeneratorStrategy),
  KQ: () => (bw_EffUsernameGeneratorStrategy),
  ji: () => (bw_ForwarderGeneratorStrategy),
  jK: () => (bw_PassphraseGeneratorStrategy),
  gb: () => (bw_PasswordGeneratorStrategy),
  Vm: () => (bw_SubaddressGeneratorStrategy)
});

;// external "commander"
const bw_external_commander_namespaceObject = require("commander");
;// external "chalk"
const bw_external_chalk_namespaceObject = require("chalk");
;// external "rxjs"
const bw_external_rxjs_namespaceObject = require("rxjs");
;// ../../libs/common/src/auth/enums/authentication-status.ts
var bw_authentication_status_AuthenticationStatus;
(function (AuthenticationStatus) {
    AuthenticationStatus[AuthenticationStatus["LoggedOut"] = 0] = "LoggedOut";
    AuthenticationStatus[AuthenticationStatus["Locked"] = 1] = "Locked";
    AuthenticationStatus[AuthenticationStatus["Unlocked"] = 2] = "Unlocked";
})(bw_authentication_status_AuthenticationStatus || (bw_authentication_status_AuthenticationStatus = {}));

;// external "path"
const bw_external_path_namespaceObject = require("path");
;// external "buffer/"
const bw_namespaceObject = require("buffer/");
;// external "tldts"
const bw_external_tldts_namespaceObject = require("tldts");
;// ../../libs/common/src/platform/misc/utils.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
/* eslint-disable no-useless-escape */




// FIXME: Remove when updating file. Eslint update
// eslint-disable-next-line @typescript-eslint/no-require-imports
const bw_nodeURL = typeof self === "undefined" ? __webpack_require__(857) : null;
class bw_utils_Utils {
    static init() {
        if (bw_utils_Utils.inited) {
            return;
        }
        bw_utils_Utils.inited = true;
        bw_utils_Utils.isNode =
            typeof process !== "undefined" &&
                process.release != null &&
                process.release.name === "node";
        bw_utils_Utils.isBrowser = typeof window !== "undefined";
        bw_utils_Utils.isMobileBrowser = bw_utils_Utils.isBrowser && this.isMobile(window);
        bw_utils_Utils.isAppleMobileBrowser = bw_utils_Utils.isBrowser && this.isAppleMobile(window);
        if (bw_utils_Utils.isNode) {
            bw_utils_Utils.global = global;
        }
        else if (bw_utils_Utils.isBrowser) {
            bw_utils_Utils.global = window;
        }
        else {
            // If it's not browser or node then it must be a service worker
            bw_utils_Utils.global = self;
        }
    }
    static fromB64ToArray(str) {
        if (str == null) {
            return null;
        }
        if (bw_utils_Utils.isNode) {
            return new Uint8Array(Buffer.from(str, "base64"));
        }
        else {
            const binaryString = bw_utils_Utils.global.atob(str);
            const bytes = new Uint8Array(binaryString.length);
            for (let i = 0; i < binaryString.length; i++) {
                bytes[i] = binaryString.charCodeAt(i);
            }
            return bytes;
        }
    }
    static fromUrlB64ToArray(str) {
        return bw_utils_Utils.fromB64ToArray(bw_utils_Utils.fromUrlB64ToB64(str));
    }
    static fromHexToArray(str) {
        if (bw_utils_Utils.isNode) {
            return new Uint8Array(Buffer.from(str, "hex"));
        }
        else {
            const bytes = new Uint8Array(str.length / 2);
            for (let i = 0; i < str.length; i += 2) {
                bytes[i / 2] = parseInt(str.substr(i, 2), 16);
            }
            return bytes;
        }
    }
    static fromUtf8ToArray(str) {
        if (bw_utils_Utils.isNode) {
            return new Uint8Array(Buffer.from(str, "utf8"));
        }
        else {
            const strUtf8 = unescape(encodeURIComponent(str));
            const arr = new Uint8Array(strUtf8.length);
            for (let i = 0; i < strUtf8.length; i++) {
                arr[i] = strUtf8.charCodeAt(i);
            }
            return arr;
        }
    }
    static fromByteStringToArray(str) {
        if (str == null) {
            return null;
        }
        const arr = new Uint8Array(str.length);
        for (let i = 0; i < str.length; i++) {
            arr[i] = str.charCodeAt(i);
        }
        return arr;
    }
    static fromBufferToB64(buffer) {
        if (buffer == null) {
            return null;
        }
        if (bw_utils_Utils.isNode) {
            return Buffer.from(buffer).toString("base64");
        }
        else {
            let binary = "";
            const bytes = new Uint8Array(buffer);
            for (let i = 0; i < bytes.byteLength; i++) {
                binary += String.fromCharCode(bytes[i]);
            }
            return bw_utils_Utils.global.btoa(binary);
        }
    }
    static fromBufferToUrlB64(buffer) {
        return bw_utils_Utils.fromB64toUrlB64(bw_utils_Utils.fromBufferToB64(buffer));
    }
    static fromB64toUrlB64(b64Str) {
        return b64Str.replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
    }
    static fromBufferToUtf8(buffer) {
        return bw_namespaceObject.Buffer.from(buffer).toString("utf8");
    }
    static fromBufferToByteString(buffer) {
        return String.fromCharCode.apply(null, new Uint8Array(buffer));
    }
    // ref: https://stackoverflow.com/a/40031979/1090359
    static fromBufferToHex(buffer) {
        if (bw_utils_Utils.isNode) {
            return Buffer.from(buffer).toString("hex");
        }
        else {
            const bytes = new Uint8Array(buffer);
            return Array.prototype.map
                .call(bytes, (x) => ("00" + x.toString(16)).slice(-2))
                .join("");
        }
    }
    /**
     * Converts a hex string to an ArrayBuffer.
     * Note: this doesn't need any Node specific code as parseInt() / ArrayBuffer / Uint8Array
     * work the same in Node and the browser.
     * @param {string} hexString - A string of hexadecimal characters.
     * @returns {ArrayBuffer} The ArrayBuffer representation of the hex string.
     */
    static hexStringToArrayBuffer(hexString) {
        // Check if the hexString has an even length, as each hex digit represents half a byte (4 bits),
        // and it takes two hex digits to represent a full byte (8 bits).
        if (hexString.length % 2 !== 0) {
            throw "HexString has to be an even length";
        }
        // Create an ArrayBuffer with a length that is half the length of the hex string,
        // because each pair of hex digits will become a single byte.
        const arrayBuffer = new ArrayBuffer(hexString.length / 2);
        // Create a Uint8Array view on top of the ArrayBuffer (each position represents a byte)
        // as ArrayBuffers cannot be edited directly.
        const uint8Array = new Uint8Array(arrayBuffer);
        // Loop through the bytes
        for (let i = 0; i < uint8Array.length; i++) {
            // Extract two hex characters (1 byte)
            const hexByte = hexString.substr(i * 2, 2);
            // Convert hexByte into a decimal value from base 16. (ex: ff --> 255)
            const byteValue = parseInt(hexByte, 16);
            // Place the byte value into the uint8Array
            uint8Array[i] = byteValue;
        }
        return arrayBuffer;
    }
    static fromUrlB64ToB64(urlB64Str) {
        let output = urlB64Str.replace(/-/g, "+").replace(/_/g, "/");
        switch (output.length % 4) {
            case 0:
                break;
            case 2:
                output += "==";
                break;
            case 3:
                output += "=";
                break;
            default:
                throw new Error("Illegal base64url string!");
        }
        return output;
    }
    static fromUrlB64ToUtf8(urlB64Str) {
        return bw_utils_Utils.fromB64ToUtf8(bw_utils_Utils.fromUrlB64ToB64(urlB64Str));
    }
    static fromUtf8ToB64(utfStr) {
        if (bw_utils_Utils.isNode) {
            return Buffer.from(utfStr, "utf8").toString("base64");
        }
        else {
            return decodeURIComponent(escape(bw_utils_Utils.global.btoa(utfStr)));
        }
    }
    static fromUtf8ToUrlB64(utfStr) {
        return bw_utils_Utils.fromBufferToUrlB64(bw_utils_Utils.fromUtf8ToArray(utfStr));
    }
    static fromB64ToUtf8(b64Str) {
        if (bw_utils_Utils.isNode) {
            return Buffer.from(b64Str, "base64").toString("utf8");
        }
        else {
            return decodeURIComponent(escape(bw_utils_Utils.global.atob(b64Str)));
        }
    }
    // ref: http://stackoverflow.com/a/2117523/1090359
    static newGuid() {
        return "xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(/[xy]/g, (c) => {
            const r = (Math.random() * 16) | 0;
            const v = c === "x" ? r : (r & 0x3) | 0x8;
            return v.toString(16);
        });
    }
    static isGuid(id) {
        return RegExp(bw_utils_Utils.guidRegex, "i").test(id);
    }
    static getHostname(uriString) {
        if (bw_utils_Utils.isNullOrWhitespace(uriString)) {
            return null;
        }
        uriString = uriString.trim();
        if (uriString.startsWith("data:")) {
            return null;
        }
        if (uriString.startsWith("about:")) {
            return null;
        }
        if (uriString.startsWith("file:")) {
            return null;
        }
        // Does uriString contain invalid characters
        // TODO Needs to possibly be extended, although '!' is a reserved character
        if (uriString.indexOf("!") > 0) {
            return null;
        }
        try {
            const hostname = (0,bw_external_tldts_namespaceObject.getHostname)(uriString, { validHosts: this.validHosts });
            if (hostname != null) {
                return hostname;
            }
        }
        catch (_a) {
            return null;
        }
        return null;
    }
    static getHost(uriString) {
        const url = bw_utils_Utils.getUrl(uriString);
        try {
            return url != null && url.host !== "" ? url.host : null;
        }
        catch (_a) {
            return null;
        }
    }
    static getDomain(uriString) {
        if (bw_utils_Utils.isNullOrWhitespace(uriString)) {
            return null;
        }
        uriString = uriString.trim();
        if (uriString.startsWith("data:")) {
            return null;
        }
        if (uriString.startsWith("about:")) {
            return null;
        }
        try {
            const parseResult = (0,bw_external_tldts_namespaceObject.parse)(uriString, {
                validHosts: this.validHosts,
                allowPrivateDomains: true,
            });
            if (parseResult != null && parseResult.hostname != null) {
                if (parseResult.hostname === "localhost" || parseResult.isIp) {
                    return parseResult.hostname;
                }
                if (parseResult.domain != null) {
                    return parseResult.domain;
                }
                return null;
            }
        }
        catch (_a) {
            return null;
        }
        return null;
    }
    static getQueryParams(uriString) {
        const url = bw_utils_Utils.getUrl(uriString);
        if (url == null || url.search == null || url.search === "") {
            return null;
        }
        const map = new Map();
        const pairs = (url.search[0] === "?" ? url.search.substr(1) : url.search).split("&");
        pairs.forEach((pair) => {
            const parts = pair.split("=");
            if (parts.length < 1) {
                return;
            }
            map.set(decodeURIComponent(parts[0]).toLowerCase(), parts[1] == null ? "" : decodeURIComponent(parts[1]));
        });
        return map;
    }
    static getSortFunction(i18nService, prop) {
        return (a, b) => {
            if (a[prop] == null && b[prop] != null) {
                return -1;
            }
            if (a[prop] != null && b[prop] == null) {
                return 1;
            }
            if (a[prop] == null && b[prop] == null) {
                return 0;
            }
            // The `as unknown as string` here is unfortunate because typescript doesn't property understand that the return of T[prop] will be a string
            return i18nService.collator
                ? i18nService.collator.compare(a[prop], b[prop])
                : a[prop].localeCompare(b[prop]);
        };
    }
    static isNullOrWhitespace(str) {
        return str == null || typeof str !== "string" || str.trim() === "";
    }
    static isNullOrEmpty(str) {
        return str == null || typeof str !== "string" || str == "";
    }
    static isPromise(obj) {
        return (obj != undefined && typeof obj["then"] === "function" && typeof obj["catch"] === "function");
    }
    static nameOf(name) {
        return name;
    }
    static assign(target, source) {
        return Object.assign(target, source);
    }
    static iterateEnum(obj) {
        return Object.keys(obj).filter((k) => Number.isNaN(+k)).map((k) => obj[k]);
    }
    static getUrl(uriString) {
        if (this.isNullOrWhitespace(uriString)) {
            return null;
        }
        uriString = uriString.trim();
        return bw_utils_Utils.getUrlObject(uriString);
    }
    static camelToPascalCase(s) {
        return s.charAt(0).toUpperCase() + s.slice(1);
    }
    /**
     * There are a few ways to calculate text color for contrast, this one seems to fit accessibility guidelines best.
     * https://stackoverflow.com/a/3943023/6869691
     *
     * @param {string} bgColor
     * @param {number} [threshold] see stackoverflow link above
     * @param {boolean} [svgTextFill]
     * Indicates if this method is performed on an SVG <text> 'fill' attribute (e.g. <text fill="black"></text>).
     * This check is necessary because the '!important' tag cannot be used in a 'fill' attribute.
     */
    static pickTextColorBasedOnBgColor(bgColor, threshold = 186, svgTextFill = false) {
        const bgColorHexNums = bgColor.charAt(0) === "#" ? bgColor.substring(1, 7) : bgColor;
        const r = parseInt(bgColorHexNums.substring(0, 2), 16); // hexToR
        const g = parseInt(bgColorHexNums.substring(2, 4), 16); // hexToG
        const b = parseInt(bgColorHexNums.substring(4, 6), 16); // hexToB
        const blackColor = svgTextFill ? "black" : "black !important";
        const whiteColor = svgTextFill ? "white" : "white !important";
        return r * 0.299 + g * 0.587 + b * 0.114 > threshold ? blackColor : whiteColor;
    }
    static stringToColor(str) {
        let hash = 0;
        for (let i = 0; i < str.length; i++) {
            hash = str.charCodeAt(i) + ((hash << 5) - hash);
        }
        let color = "#";
        for (let i = 0; i < 3; i++) {
            const value = (hash >> (i * 8)) & 0xff;
            color += ("00" + value.toString(16)).substr(-2);
        }
        return color;
    }
    /**
     * @throws Will throw an error if the ContainerService has not been attached to the window object
     */
    static getContainerService() {
        if (this.global.bitwardenContainerService == null) {
            throw new Error("global bitwardenContainerService not initialized.");
        }
        return this.global.bitwardenContainerService;
    }
    static validateHexColor(color) {
        return /^#([A-Fa-f0-9]{6}|[A-Fa-f0-9]{3})$/.test(color);
    }
    /**
     * Converts map to a Record<string, V> with the same data. Inverse of recordToMap
     * Useful in toJSON methods, since Maps are not serializable
     * @param map
     * @returns
     */
    static mapToRecord(map) {
        if (map == null) {
            return null;
        }
        if (!(map instanceof Map)) {
            return map;
        }
        return Object.fromEntries(map);
    }
    /**
     * Converts record to a Map<string, V> with the same data. Inverse of mapToRecord
     * Useful in fromJSON methods, since Maps are not serializable
     *
     * Warning: If the record has string keys that are numbers, they will be converted to numbers in the map
     * @param record
     * @returns
     */
    static recordToMap(record) {
        if (record == null) {
            return null;
        }
        else if (record instanceof Map) {
            return record;
        }
        const entries = Object.entries(record);
        if (entries.length === 0) {
            return new Map();
        }
        if (isNaN(Number(entries[0][0]))) {
            return new Map(entries);
        }
        else {
            return new Map(entries.map((e) => [Number(e[0]), e[1]]));
        }
    }
    /** Applies Object.assign, but converts the type nicely using Type-Fest Merge<Destination, Source> */
    static merge(destination, source) {
        return Object.assign(destination, source);
    }
    /**
     * encodeURIComponent escapes all characters except the following:
     * alphabetic, decimal digits, - _ . ! ~ * ' ( )
     * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent#encoding_for_rfc3986
     */
    static encodeRFC3986URIComponent(str) {
        return encodeURIComponent(str).replace(/[!'()*]/g, (c) => `%${c.charCodeAt(0).toString(16).toUpperCase()}`);
    }
    /**
     * Normalizes a path for defense against attacks like traversals
     * @param denormalizedPath
     * @returns
     */
    static normalizePath(denormalizedPath) {
        return bw_external_path_namespaceObject.normalize(decodeURIComponent(denormalizedPath)).replace(/^(\.\.(\/|\\|$))+/, "");
    }
    static isMobile(win) {
        let mobile = false;
        ((a) => {
            if (/(android|bb\d+|meego).+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows ce|xda|xiino/i.test(a) ||
                /1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i.test(a.substr(0, 4))) {
                mobile = true;
            }
        })(win.navigator.userAgent || win.navigator.vendor || win.opera);
        return mobile || win.navigator.userAgent.match(/iPad/i) != null;
    }
    static delay(ms) {
        return new Promise((resolve) => setTimeout(resolve, ms));
    }
    /**
     * Generate an observable from a function that returns a promise.
     * Similar to the rxjs function {@link from} with one big exception:
     * {@link from} will not re-execute the function when observers resubscribe.
     * {@link Util.asyncToObservable} will execute `generator` for every
     * subscribe, making it ideal if the value ever needs to be refreshed.
     * */
    static asyncToObservable(generator) {
        return (0,bw_external_rxjs_namespaceObject.of)(undefined).pipe((0,bw_external_rxjs_namespaceObject.switchMap)(() => generator()));
    }
    /**
     * Return the number of days remaining before a target date arrives.
     * Returns 0 if the day has already passed.
     */
    static daysRemaining(targetDate) {
        const diffTime = targetDate.getTime() - Date.now();
        const msPerDay = 86400000;
        return Math.max(0, Math.floor(diffTime / msPerDay));
    }
    static isAppleMobile(win) {
        return (win.navigator.userAgent.match(/iPhone/i) != null ||
            win.navigator.userAgent.match(/iPad/i) != null);
    }
    static getUrlObject(uriString) {
        // All the methods below require a protocol to properly parse a URL string
        // Assume http if no other protocol is present
        const hasProtocol = uriString.indexOf("://") > -1;
        if (!hasProtocol && uriString.indexOf(".") > -1) {
            uriString = "http://" + uriString;
        }
        else if (!hasProtocol) {
            return null;
        }
        try {
            if (bw_nodeURL != null) {
                return new bw_nodeURL.URL(uriString);
            }
            return new URL(uriString);
            // FIXME: Remove when updating file. Eslint update
            // eslint-disable-next-line @typescript-eslint/no-unused-vars
        }
        catch (e) {
            // Ignore error
        }
        return null;
    }
}
bw_utils_Utils.inited = false;
bw_utils_Utils.isNode = false;
bw_utils_Utils.isBrowser = true;
bw_utils_Utils.isMobileBrowser = false;
bw_utils_Utils.isAppleMobileBrowser = false;
bw_utils_Utils.global = null;
// Transpiled version of /\p{Emoji_Presentation}/gu using https://mothereff.in/regexpu. Used for compatability in older browsers.
bw_utils_Utils.regexpEmojiPresentation = /(?:[\u231A\u231B\u23E9-\u23EC\u23F0\u23F3\u25FD\u25FE\u2614\u2615\u2648-\u2653\u267F\u2693\u26A1\u26AA\u26AB\u26BD\u26BE\u26C4\u26C5\u26CE\u26D4\u26EA\u26F2\u26F3\u26F5\u26FA\u26FD\u2705\u270A\u270B\u2728\u274C\u274E\u2753-\u2755\u2757\u2795-\u2797\u27B0\u27BF\u2B1B\u2B1C\u2B50\u2B55]|\uD83C[\uDC04\uDCCF\uDD8E\uDD91-\uDD9A\uDDE6-\uDDFF\uDE01\uDE1A\uDE2F\uDE32-\uDE36\uDE38-\uDE3A\uDE50\uDE51\uDF00-\uDF20\uDF2D-\uDF35\uDF37-\uDF7C\uDF7E-\uDF93\uDFA0-\uDFCA\uDFCF-\uDFD3\uDFE0-\uDFF0\uDFF4\uDFF8-\uDFFF]|\uD83D[\uDC00-\uDC3E\uDC40\uDC42-\uDCFC\uDCFF-\uDD3D\uDD4B-\uDD4E\uDD50-\uDD67\uDD7A\uDD95\uDD96\uDDA4\uDDFB-\uDE4F\uDE80-\uDEC5\uDECC\uDED0-\uDED2\uDED5-\uDED7\uDEEB\uDEEC\uDEF4-\uDEFC\uDFE0-\uDFEB]|\uD83E[\uDD0C-\uDD3A\uDD3C-\uDD45\uDD47-\uDD78\uDD7A-\uDDCB\uDDCD-\uDDFF\uDE70-\uDE74\uDE78-\uDE7A\uDE80-\uDE86\uDE90-\uDEA8\uDEB0-\uDEB6\uDEC0-\uDEC2\uDED0-\uDED6])/g;
bw_utils_Utils.validHosts = ["localhost"];
bw_utils_Utils.originalMinimumPasswordLength = 8;
bw_utils_Utils.minimumPasswordLength = 12;
bw_utils_Utils.DomainMatchBlacklist = new Map([
    ["google.com", new Set(["script.google.com"])],
]);
bw_utils_Utils.guidRegex = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/;
bw_utils_Utils.init();

;// ../../libs/common/src/models/response/base.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_BaseResponse {
    constructor(response) {
        this.response = response;
    }
    getResponseProperty(propertyName, response = null, exactName = false) {
        if (propertyName == null || propertyName === "") {
            throw new Error("propertyName must not be null/empty.");
        }
        if (response == null && this.response != null) {
            response = this.response;
        }
        if (response == null) {
            return null;
        }
        if (!exactName && response[propertyName] === undefined) {
            let otherCasePropertyName = null;
            if (propertyName.charAt(0) === propertyName.charAt(0).toUpperCase()) {
                otherCasePropertyName = propertyName.charAt(0).toLowerCase();
            }
            else {
                otherCasePropertyName = propertyName.charAt(0).toUpperCase();
            }
            if (propertyName.length > 1) {
                otherCasePropertyName += propertyName.slice(1);
            }
            propertyName = otherCasePropertyName;
            if (response[propertyName] === undefined) {
                propertyName = propertyName.toLowerCase();
            }
            if (response[propertyName] === undefined) {
                propertyName = propertyName.toUpperCase();
            }
        }
        return response[propertyName];
    }
}

;// ../../libs/common/src/models/response/error.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_ErrorResponse extends bw_BaseResponse {
    constructor(response, status, identityResponse) {
        var _a, _b;
        super(response);
        let errorModel = null;
        if (response != null) {
            const responseErrorModel = this.getResponseProperty("ErrorModel");
            if (responseErrorModel && identityResponse) {
                errorModel = responseErrorModel;
            }
            else {
                errorModel = response;
            }
        }
        if (status === 429) {
            this.message = "Rate limit exceeded. Try again later.";
        }
        else if (errorModel) {
            this.message = this.getResponseProperty("Message", errorModel);
            this.validationErrors = this.getResponseProperty("ValidationErrors", errorModel);
            this.captchaSiteKey = (_b = (_a = this.validationErrors) === null || _a === void 0 ? void 0 : _a.HCaptcha_SiteKey) === null || _b === void 0 ? void 0 : _b[0];
            this.captchaRequired = !bw_utils_Utils.isNullOrWhitespace(this.captchaSiteKey);
        }
        this.statusCode = status;
    }
    getSingleMessage() {
        if (this.validationErrors == null) {
            return this.message;
        }
        for (const key in this.validationErrors) {
            // eslint-disable-next-line
            if (!this.validationErrors.hasOwnProperty(key)) {
                continue;
            }
            if (this.validationErrors[key].length) {
                return this.validationErrors[key][0];
            }
        }
        return this.message;
    }
    getAllMessages() {
        const messages = [];
        if (this.validationErrors == null) {
            return messages;
        }
        for (const key in this.validationErrors) {
            // eslint-disable-next-line
            if (!this.validationErrors.hasOwnProperty(key)) {
                continue;
            }
            this.validationErrors[key].forEach((item) => {
                let prefix = "";
                if (key.indexOf("[") > -1 && key.indexOf("]") > -1) {
                    const lastSep = key.lastIndexOf(".");
                    prefix = key.substr(0, lastSep > -1 ? lastSep : key.length) + ": ";
                }
                messages.push(prefix + item);
            });
        }
        return messages;
    }
}

;// ./src/models/response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

function bw_getErrorMessage(error) {
    if (typeof error === "string") {
        return error;
    }
    if (error instanceof bw_ErrorResponse) {
        const message = error.getSingleMessage();
        if (message) {
            return message;
        }
    }
    if (error instanceof Error) {
        return String(error);
    }
    if (error) {
        const errorWithMessage = error; // To placate TypeScript.
        if (errorWithMessage.message && typeof errorWithMessage.message === "string") {
            return errorWithMessage.message;
        }
    }
    return JSON.stringify(error);
}
class bw_Response {
    static error(error, data) {
        const res = new bw_Response();
        res.success = false;
        res.message = bw_getErrorMessage(error);
        res.data = data;
        return res;
    }
    static notFound() {
        return bw_Response.error("Not found.");
    }
    static noEditPermission() {
        return bw_Response.error("You do not have permission to edit this item");
    }
    static badRequest(message) {
        return bw_Response.error(message);
    }
    static multipleResults(ids) {
        let msg = "More than one result was found. Try getting a specific object by `id` instead. " +
            "The following objects were found:";
        ids.forEach((id) => {
            msg += "\n" + id;
        });
        return bw_Response.error(msg, ids);
    }
    static success(data) {
        const res = new bw_Response();
        res.success = true;
        res.data = data;
        return res;
    }
}

;// ./src/models/response/message.response.ts
class bw_MessageResponse {
    constructor(title, message) {
        this.noColor = false;
        this.object = "message";
        this.title = title;
        this.message = message;
    }
}

;// ./src/auth/commands/lock.command.ts
var src_bw_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_LockCommand {
    constructor(vaultTimeoutService) {
        this.vaultTimeoutService = vaultTimeoutService;
    }
    run() {
        return src_bw_awaiter(this, void 0, void 0, function* () {
            yield this.vaultTimeoutService.lock();
            process.env.BW_SESSION = null;
            const res = new bw_MessageResponse("Your vault is locked.", null);
            return bw_Response.success(res);
        });
    }
}

;// external "http"
const bw_external_http_namespaceObject = require("http");
;// external "inquirer"
const bw_external_inquirer_namespaceObject = require("inquirer");
;// ../../libs/common/src/auth/enums/authentication-type.ts
var bw_AuthenticationType;
(function (AuthenticationType) {
    AuthenticationType[AuthenticationType["Password"] = 0] = "Password";
    AuthenticationType[AuthenticationType["Sso"] = 1] = "Sso";
    AuthenticationType[AuthenticationType["UserApiKey"] = 2] = "UserApiKey";
    AuthenticationType[AuthenticationType["AuthRequest"] = 3] = "AuthRequest";
    AuthenticationType[AuthenticationType["WebAuthn"] = 4] = "WebAuthn";
})(bw_AuthenticationType || (bw_AuthenticationType = {}));

;// ../../libs/common/src/auth/models/request/identity-token/token-two-factor.request.ts
class bw_TokenTwoFactorRequest {
    constructor(provider = null, token = null, remember = false) {
        this.provider = provider;
        this.token = token;
        this.remember = remember;
    }
}

;// ../../libs/common/src/auth/services/webauthn-login/request/webauthn-login-response.request.ts

class bw_WebAuthnLoginResponseRequest {
    constructor(credential) {
        this.id = credential.id;
        this.rawId = bw_utils_Utils.fromBufferToUrlB64(credential.rawId);
        this.type = credential.type;
        // WARNING: do not add PRF information here by mapping
        // credential.getClientExtensionResults() into the extensions property,
        // as it will be sent to the server (leaking credentials).
        this.extensions = {}; // Extensions are handled client-side
    }
}

;// ../../libs/common/src/auth/services/webauthn-login/request/webauthn-login-assertion-response.request.ts


class bw_WebAuthnLoginAssertionResponseRequest extends bw_WebAuthnLoginResponseRequest {
    constructor(credential) {
        super(credential);
        if (!(credential.response instanceof AuthenticatorAssertionResponse)) {
            throw new Error("Invalid authenticator response");
        }
        this.response = {
            authenticatorData: bw_utils_Utils.fromBufferToUrlB64(credential.response.authenticatorData),
            signature: bw_utils_Utils.fromBufferToUrlB64(credential.response.signature),
            clientDataJSON: bw_utils_Utils.fromBufferToUrlB64(credential.response.clientDataJSON),
            userHandle: bw_utils_Utils.fromBufferToUrlB64(credential.response.userHandle),
        };
    }
    static fromJSON(json) {
        return Object.assign(Object.create(bw_WebAuthnLoginAssertionResponseRequest.prototype), json);
    }
}

;// ../../libs/common/src/platform/enums/encryption-type.enum.ts
var bw_EncryptionType;
(function (EncryptionType) {
    EncryptionType[EncryptionType["AesCbc256_B64"] = 0] = "AesCbc256_B64";
    // Type 1 was the unused and removed AesCbc128_HmacSha256_B64
    EncryptionType[EncryptionType["AesCbc256_HmacSha256_B64"] = 2] = "AesCbc256_HmacSha256_B64";
    EncryptionType[EncryptionType["Rsa2048_OaepSha256_B64"] = 3] = "Rsa2048_OaepSha256_B64";
    EncryptionType[EncryptionType["Rsa2048_OaepSha1_B64"] = 4] = "Rsa2048_OaepSha1_B64";
    EncryptionType[EncryptionType["Rsa2048_OaepSha256_HmacSha256_B64"] = 5] = "Rsa2048_OaepSha256_HmacSha256_B64";
    EncryptionType[EncryptionType["Rsa2048_OaepSha1_HmacSha256_B64"] = 6] = "Rsa2048_OaepSha1_HmacSha256_B64";
})(bw_EncryptionType || (bw_EncryptionType = {}));
function bw_encryptionTypeToString(encryptionType) {
    if (encryptionType in bw_EncryptionType) {
        return bw_EncryptionType[encryptionType];
    }
    else {
        return "Unknown encryption type " + encryptionType;
    }
}
/** The expected number of parts to a serialized EncString of the given encryption type.
 * For example, an EncString of type AesCbc256_B64 will have 2 parts
 *
 * Example of annotated serialized EncStrings:
 * 0.iv|data
 * 2.iv|data|mac
 * 3.data
 * 4.data
 *
 * @see EncString
 * @see EncryptionType
 * @see EncString.parseEncryptedString
 */
const bw_EXPECTED_NUM_PARTS_BY_ENCRYPTION_TYPE = {
    [bw_EncryptionType.AesCbc256_B64]: 2,
    [bw_EncryptionType.AesCbc256_HmacSha256_B64]: 3,
    [bw_EncryptionType.Rsa2048_OaepSha256_B64]: 1,
    [bw_EncryptionType.Rsa2048_OaepSha1_B64]: 1,
    [bw_EncryptionType.Rsa2048_OaepSha256_HmacSha256_B64]: 2,
    [bw_EncryptionType.Rsa2048_OaepSha1_HmacSha256_B64]: 2,
};

;// ../../libs/common/src/platform/enums/file-upload-type.enum.ts
var bw_FileUploadType;
(function (FileUploadType) {
    FileUploadType[FileUploadType["Direct"] = 0] = "Direct";
    FileUploadType[FileUploadType["Azure"] = 1] = "Azure";
})(bw_FileUploadType || (bw_FileUploadType = {}));

;// ../../libs/common/src/platform/enums/hash-purpose.enum.ts
var bw_HashPurpose;
(function (HashPurpose) {
    HashPurpose[HashPurpose["ServerAuthorization"] = 1] = "ServerAuthorization";
    HashPurpose[HashPurpose["LocalAuthorization"] = 2] = "LocalAuthorization";
})(bw_HashPurpose || (bw_HashPurpose = {}));

;// ../../libs/common/src/platform/enums/html-storage-location.enum.ts
var bw_HtmlStorageLocation;
(function (HtmlStorageLocation) {
    HtmlStorageLocation["Local"] = "local";
    HtmlStorageLocation["Memory"] = "memory";
    HtmlStorageLocation["Session"] = "session";
})(bw_HtmlStorageLocation || (bw_HtmlStorageLocation = {}));

;// ../../libs/common/src/platform/enums/key-suffix-options.enum.ts
var bw_KeySuffixOptions;
(function (KeySuffixOptions) {
    KeySuffixOptions["Auto"] = "auto";
    KeySuffixOptions["Pin"] = "pin";
})(bw_KeySuffixOptions || (bw_KeySuffixOptions = {}));

;// ../../libs/common/src/platform/enums/log-level-type.enum.ts
var bw_LogLevelType;
(function (LogLevelType) {
    LogLevelType[LogLevelType["Debug"] = 0] = "Debug";
    LogLevelType[LogLevelType["Info"] = 1] = "Info";
    LogLevelType[LogLevelType["Warning"] = 2] = "Warning";
    LogLevelType[LogLevelType["Error"] = 3] = "Error";
})(bw_LogLevelType || (bw_LogLevelType = {}));

;// ../../libs/common/src/platform/enums/storage-location.enum.ts
var bw_StorageLocation;
(function (StorageLocation) {
    StorageLocation["Both"] = "both";
    StorageLocation["Disk"] = "disk";
    StorageLocation["Memory"] = "memory";
})(bw_StorageLocation || (bw_StorageLocation = {}));

;// ../../libs/common/src/platform/enums/theme-type.enum.ts
/**
 * @deprecated prefer the `ThemeTypes` constants and `Theme` type over unsafe enum types
 **/
var bw_ThemeType;
(function (ThemeType) {
    ThemeType["System"] = "system";
    ThemeType["Light"] = "light";
    ThemeType["Dark"] = "dark";
})(bw_ThemeType || (bw_ThemeType = {}));
const bw_ThemeTypes = {
    System: "system",
    Light: "light",
    Dark: "dark",
};

;// ../../libs/common/src/platform/enums/index.ts









;// ../../libs/common/src/platform/models/domain/symmetric-crypto-key.ts


class bw_SymmetricCryptoKey {
    constructor(key, encType) {
        if (key == null) {
            throw new Error("Must provide key");
        }
        if (encType == null) {
            if (key.byteLength === 32) {
                encType = bw_EncryptionType.AesCbc256_B64;
            }
            else if (key.byteLength === 64) {
                encType = bw_EncryptionType.AesCbc256_HmacSha256_B64;
            }
            else {
                throw new Error("Unable to determine encType.");
            }
        }
        this.key = key;
        this.encType = encType;
        if (encType === bw_EncryptionType.AesCbc256_B64 && key.byteLength === 32) {
            this.encKey = key;
            this.macKey = null;
        }
        else if (encType === bw_EncryptionType.AesCbc256_HmacSha256_B64 && key.byteLength === 64) {
            this.encKey = key.slice(0, 32);
            this.macKey = key.slice(32, 64);
        }
        else {
            throw new Error("Unsupported encType/key length.");
        }
        this.keyB64 = bw_utils_Utils.fromBufferToB64(this.key);
        this.encKeyB64 = bw_utils_Utils.fromBufferToB64(this.encKey);
        if (this.macKey != null) {
            this.macKeyB64 = bw_utils_Utils.fromBufferToB64(this.macKey);
        }
    }
    toJSON() {
        // The whole object is constructed from the initial key, so just store the B64 key
        return { keyB64: this.keyB64 };
    }
    static fromString(s) {
        if (s == null) {
            return null;
        }
        const arrayBuffer = bw_utils_Utils.fromB64ToArray(s);
        return new bw_SymmetricCryptoKey(arrayBuffer);
    }
    static fromJSON(obj) {
        return bw_SymmetricCryptoKey.fromString(obj === null || obj === void 0 ? void 0 : obj.keyB64);
    }
}

;// ../../libs/auth/src/common/models/domain/login-credentials.ts




class bw_PasswordLoginCredentials {
    constructor(email, masterPassword, 
    // TODO: PM-15162 - captcha is deprecated as part of UI refresh work
    captchaToken, twoFactor) {
        this.email = email;
        this.masterPassword = masterPassword;
        this.captchaToken = captchaToken;
        this.twoFactor = twoFactor;
        this.type = bw_AuthenticationType.Password;
    }
}
class bw_SsoLoginCredentials {
    constructor(code, codeVerifier, redirectUrl, orgId, 
    /**
     * Optional email address for SSO login.
     * Used for looking up 2FA token on clients that support remembering 2FA token.
     */
    email, twoFactor) {
        this.code = code;
        this.codeVerifier = codeVerifier;
        this.redirectUrl = redirectUrl;
        this.orgId = orgId;
        this.email = email;
        this.twoFactor = twoFactor;
        this.type = bw_AuthenticationType.Sso;
    }
}
class bw_UserApiLoginCredentials {
    constructor(clientId, clientSecret) {
        this.clientId = clientId;
        this.clientSecret = clientSecret;
        this.type = bw_AuthenticationType.UserApiKey;
    }
}
class bw_AuthRequestLoginCredentials {
    constructor(email, accessCode, authRequestId, decryptedUserKey, decryptedMasterKey, decryptedMasterKeyHash, twoFactor) {
        this.email = email;
        this.accessCode = accessCode;
        this.authRequestId = authRequestId;
        this.decryptedUserKey = decryptedUserKey;
        this.decryptedMasterKey = decryptedMasterKey;
        this.decryptedMasterKeyHash = decryptedMasterKeyHash;
        this.twoFactor = twoFactor;
        this.type = bw_AuthenticationType.AuthRequest;
    }
    static fromJSON(json) {
        return Object.assign(new bw_AuthRequestLoginCredentials(json.email, json.accessCode, json.authRequestId, null, null, json.decryptedMasterKeyHash, json.twoFactor
            ? new bw_TokenTwoFactorRequest(json.twoFactor.provider, json.twoFactor.token, json.twoFactor.remember)
            : json.twoFactor), {
            decryptedUserKey: bw_SymmetricCryptoKey.fromJSON(json.decryptedUserKey),
            decryptedMasterKey: bw_SymmetricCryptoKey.fromJSON(json.decryptedMasterKey),
        });
    }
}
class bw_WebAuthnLoginCredentials {
    constructor(token, deviceResponse, prfKey) {
        this.token = token;
        this.deviceResponse = deviceResponse;
        this.prfKey = prfKey;
        this.type = bw_AuthenticationType.WebAuthn;
    }
    static fromJSON(json) {
        return new bw_WebAuthnLoginCredentials(json.token, Object.assign(Object.create(bw_WebAuthnLoginAssertionResponseRequest.prototype), json.deviceResponse), bw_SymmetricCryptoKey.fromJSON(json.prfKey));
    }
}

;// ../../libs/auth/src/common/models/domain/user-decryption-options.ts
/**
 * Key Connector decryption options. Intended to be sent to the client for use after authentication.
 * @see {@link UserDecryptionOptions}
 */
class bw_KeyConnectorUserDecryptionOption {
    /**
     * Initializes a new instance of the KeyConnectorUserDecryptionOption from a response object.
     * @param response The key connector user decryption option response object.
     * @returns A new instance of the KeyConnectorUserDecryptionOption or undefined if `response` is nullish.
     */
    static fromResponse(response) {
        var _a;
        if (response == null) {
            return undefined;
        }
        const options = new bw_KeyConnectorUserDecryptionOption();
        options.keyConnectorUrl = (_a = response === null || response === void 0 ? void 0 : response.keyConnectorUrl) !== null && _a !== void 0 ? _a : null;
        return options;
    }
    /**
     * Initializes a new instance of a KeyConnectorUserDecryptionOption from a JSON object.
     * @param obj JSON object to deserialize.
     * @returns A new instance of the KeyConnectorUserDecryptionOption or undefined if `obj` is nullish.
     */
    static fromJSON(obj) {
        if (obj == null) {
            return undefined;
        }
        return Object.assign(new bw_KeyConnectorUserDecryptionOption(), obj);
    }
}
/**
 * Trusted device decryption options. Intended to be sent to the client for use after authentication.
 * @see {@link UserDecryptionOptions}
 */
class bw_TrustedDeviceUserDecryptionOption {
    /**
     * Initializes a new instance of the TrustedDeviceUserDecryptionOption from a response object.
     * @param response The trusted device user decryption option response object.
     * @returns A new instance of the TrustedDeviceUserDecryptionOption or undefined if `response` is nullish.
     */
    static fromResponse(response) {
        var _a, _b, _c, _d;
        if (response == null) {
            return undefined;
        }
        const options = new bw_TrustedDeviceUserDecryptionOption();
        options.hasAdminApproval = (_a = response === null || response === void 0 ? void 0 : response.hasAdminApproval) !== null && _a !== void 0 ? _a : false;
        options.hasLoginApprovingDevice = (_b = response === null || response === void 0 ? void 0 : response.hasLoginApprovingDevice) !== null && _b !== void 0 ? _b : false;
        options.hasManageResetPasswordPermission = (_c = response === null || response === void 0 ? void 0 : response.hasManageResetPasswordPermission) !== null && _c !== void 0 ? _c : false;
        options.isTdeOffboarding = (_d = response === null || response === void 0 ? void 0 : response.isTdeOffboarding) !== null && _d !== void 0 ? _d : false;
        return options;
    }
    /**
     * Initializes a new instance of the TrustedDeviceUserDecryptionOption from a JSON object.
     * @param obj JSON object to deserialize.
     * @returns A new instance of the TrustedDeviceUserDecryptionOption or undefined if `obj` is nullish.
     */
    static fromJSON(obj) {
        if (obj == null) {
            return undefined;
        }
        return Object.assign(new bw_TrustedDeviceUserDecryptionOption(), obj);
    }
}
/**
 * Represents the decryption options the user has configured on the server. This is intended to be sent
 * to the client on authentication, and can be used to determine how to decrypt the user's vault.
 */
class bw_UserDecryptionOptions {
    /**
     * Initializes a new instance of the UserDecryptionOptions from a response object.
     * @param response user decryption options response object
     * @returns A new instance of the UserDecryptionOptions.
     * @throws If the response is nullish, this method will throw an error. User decryption options
     * are required for client initialization.
     */
    // TODO: Change response type to `UserDecryptionOptionsResponse` after 2023.10 release (https://bitwarden.atlassian.net/browse/PM-3537)
    static fromResponse(response) {
        if (response == null) {
            throw new Error("User Decryption Options are required for client initialization.");
        }
        const decryptionOptions = new bw_UserDecryptionOptions();
        if (response.userDecryptionOptions) {
            // If the response has userDecryptionOptions, this means it's on a post-TDE server version and can interrogate
            // the new decryption options.
            const responseOptions = response.userDecryptionOptions;
            decryptionOptions.hasMasterPassword = responseOptions.hasMasterPassword;
            decryptionOptions.trustedDeviceOption = bw_TrustedDeviceUserDecryptionOption.fromResponse(responseOptions.trustedDeviceOption);
            decryptionOptions.keyConnectorOption = bw_KeyConnectorUserDecryptionOption.fromResponse(responseOptions.keyConnectorOption);
        }
        else {
            // If the response does not have userDecryptionOptions, this means it's on a pre-TDE server version and so
            // we must base our decryption options on the presence of the keyConnectorUrl.
            // Note that the presence of keyConnectorUrl implies that the user does not have a master password, as in pre-TDE
            // server versions, a master password short-circuited the addition of the keyConnectorUrl to the response.
            // TODO: remove this check after 2023.10 release (https://bitwarden.atlassian.net/browse/PM-3537)
            const usingKeyConnector = response.keyConnectorUrl != null;
            decryptionOptions.hasMasterPassword = !usingKeyConnector;
            if (usingKeyConnector) {
                decryptionOptions.keyConnectorOption = new bw_KeyConnectorUserDecryptionOption();
                decryptionOptions.keyConnectorOption.keyConnectorUrl = response.keyConnectorUrl;
            }
        }
        return decryptionOptions;
    }
    /**
     * Initializes a new instance of the UserDecryptionOptions from a JSON object.
     * @param obj JSON object to deserialize.
     * @returns A new instance of the UserDecryptionOptions. Will initialize even if the JSON object is nullish.
     */
    static fromJSON(obj) {
        const decryptionOptions = Object.assign(new bw_UserDecryptionOptions(), obj);
        decryptionOptions.trustedDeviceOption = bw_TrustedDeviceUserDecryptionOption.fromJSON(obj === null || obj === void 0 ? void 0 : obj.trustedDeviceOption);
        decryptionOptions.keyConnectorOption = bw_KeyConnectorUserDecryptionOption.fromJSON(obj === null || obj === void 0 ? void 0 : obj.keyConnectorOption);
        return decryptionOptions;
    }
}

;// ../../libs/auth/src/common/models/domain/index.ts




;// ../../libs/auth/src/common/models/spec/fake-user-decryption-options.ts

// To discourage creating new user decryption options, we don't expose a constructor.
// These helpers are for testing purposes only.
/** Testing helper for creating new instances of `UserDecryptionOptions` */
class bw_FakeUserDecryptionOptions extends bw_UserDecryptionOptions {
    constructor(init) {
        super();
        Object.assign(this, init);
    }
}
/** Testing helper for creating new instances of `KeyConnectorUserDecryptionOption` */
class bw_FakeKeyConnectorUserDecryptionOption extends bw_KeyConnectorUserDecryptionOption {
    constructor(keyConnectorUrl) {
        super();
        this.keyConnectorUrl = keyConnectorUrl;
    }
}
/** Testing helper for creating new instances of `TrustedDeviceUserDecryptionOption` */
class bw_FakeTrustedDeviceUserDecryptionOption extends bw_TrustedDeviceUserDecryptionOption {
    constructor(hasAdminApproval, hasLoginApprovingDevice, hasManageResetPasswordPermission, isTdeOffboarding) {
        super();
        this.hasAdminApproval = hasAdminApproval;
        this.hasLoginApprovingDevice = hasLoginApprovingDevice;
        this.hasManageResetPasswordPermission = hasManageResetPasswordPermission;
        this.isTdeOffboarding = isTdeOffboarding;
    }
}

;// ../../libs/auth/src/common/models/spec/index.ts


;// ../../libs/auth/src/common/models/index.ts



;// ../../libs/common/src/platform/models/domain/enc-string.ts
var bw_enc_string_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


const bw_DECRYPT_ERROR = "[error: cannot decrypt]";
class bw_enc_string_EncString {
    constructor(encryptedStringOrType, data, iv, mac) {
        if (data != null) {
            this.initFromData(encryptedStringOrType, data, iv, mac);
        }
        else {
            this.initFromEncryptedString(encryptedStringOrType);
        }
    }
    get ivBytes() {
        return this.iv == null ? null : bw_utils_Utils.fromB64ToArray(this.iv);
    }
    get macBytes() {
        return this.mac == null ? null : bw_utils_Utils.fromB64ToArray(this.mac);
    }
    get dataBytes() {
        return this.data == null ? null : bw_utils_Utils.fromB64ToArray(this.data);
    }
    toJSON() {
        return this.encryptedString;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return new bw_enc_string_EncString(obj);
    }
    initFromData(encType, data, iv, mac) {
        if (iv != null) {
            this.encryptedString = (encType + "." + iv + "|" + data);
        }
        else {
            this.encryptedString = (encType + "." + data);
        }
        // mac
        if (mac != null) {
            this.encryptedString = (this.encryptedString + "|" + mac);
        }
        this.encryptionType = encType;
        this.data = data;
        this.iv = iv;
        this.mac = mac;
    }
    initFromEncryptedString(encryptedString) {
        this.encryptedString = encryptedString;
        if (!this.encryptedString) {
            return;
        }
        const { encType, encPieces } = bw_enc_string_EncString.parseEncryptedString(this.encryptedString);
        this.encryptionType = encType;
        if (encPieces.length !== bw_EXPECTED_NUM_PARTS_BY_ENCRYPTION_TYPE[encType]) {
            return;
        }
        switch (encType) {
            case bw_EncryptionType.AesCbc256_HmacSha256_B64:
                this.iv = encPieces[0];
                this.data = encPieces[1];
                this.mac = encPieces[2];
                break;
            case bw_EncryptionType.AesCbc256_B64:
                this.iv = encPieces[0];
                this.data = encPieces[1];
                break;
            case bw_EncryptionType.Rsa2048_OaepSha256_B64:
            case bw_EncryptionType.Rsa2048_OaepSha1_B64:
                this.data = encPieces[0];
                break;
            case bw_EncryptionType.Rsa2048_OaepSha256_HmacSha256_B64:
            case bw_EncryptionType.Rsa2048_OaepSha1_HmacSha256_B64:
                this.data = encPieces[0];
                this.mac = encPieces[1];
                break;
            default:
                return;
        }
    }
    static parseEncryptedString(encryptedString) {
        const headerPieces = encryptedString.split(".");
        let encType;
        let encPieces = null;
        if (headerPieces.length === 2) {
            try {
                encType = parseInt(headerPieces[0], null);
                encPieces = headerPieces[1].split("|");
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                return { encType: NaN, encPieces: [] };
            }
        }
        else {
            encPieces = encryptedString.split("|");
            encType = bw_EncryptionType.AesCbc256_B64;
        }
        return {
            encType,
            encPieces,
        };
    }
    static isSerializedEncString(s) {
        if (s == null) {
            return false;
        }
        const { encType, encPieces } = this.parseEncryptedString(s);
        if (isNaN(encType) || encPieces.length === 0) {
            return false;
        }
        return bw_EXPECTED_NUM_PARTS_BY_ENCRYPTION_TYPE[encType] === encPieces.length;
    }
    decrypt(orgId_1) {
        return bw_enc_string_awaiter(this, arguments, void 0, function* (orgId, key = null, context) {
            if (this.decryptedValue != null) {
                return this.decryptedValue;
            }
            let decryptTrace = "provided-key";
            try {
                if (key == null) {
                    key = yield this.getKeyForDecryption(orgId);
                    decryptTrace = orgId == null ? `domain-orgkey-${orgId}` : "domain-userkey|masterkey";
                    if (orgId != null) {
                        decryptTrace = `domain-orgkey-${orgId}`;
                    }
                    else {
                        const cryptoService = bw_utils_Utils.getContainerService().getKeyService();
                        decryptTrace =
                            (yield cryptoService.getUserKey()) == null
                                ? "domain-withlegacysupport-masterkey"
                                : "domain-withlegacysupport-userkey";
                    }
                }
                if (key == null) {
                    throw new Error("No key to decrypt EncString with orgId " + orgId);
                }
                const encryptService = bw_utils_Utils.getContainerService().getEncryptService();
                this.decryptedValue = yield encryptService.decryptToUtf8(this, key, decryptTrace == null ? context : `${decryptTrace}${context || ""}`);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                this.decryptedValue = bw_DECRYPT_ERROR;
            }
            return this.decryptedValue;
        });
    }
    decryptWithKey(key_1, encryptService_1) {
        return bw_enc_string_awaiter(this, arguments, void 0, function* (key, encryptService, decryptTrace = "domain-withkey") {
            try {
                if (key == null) {
                    throw new Error("No key to decrypt EncString");
                }
                this.decryptedValue = yield encryptService.decryptToUtf8(this, key, decryptTrace);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                this.decryptedValue = bw_DECRYPT_ERROR;
            }
            return this.decryptedValue;
        });
    }
    getKeyForDecryption(orgId) {
        return bw_enc_string_awaiter(this, void 0, void 0, function* () {
            const keyService = bw_utils_Utils.getContainerService().getKeyService();
            return orgId != null
                ? yield keyService.getOrgKey(orgId)
                : yield keyService.getUserKeyWithLegacySupport();
        });
    }
}

;// ../../libs/common/src/platform/state/derive-definition.ts
/**
 * DeriveDefinitions describe state derived from another observable, the value type of which is given by `TFrom`.
 *
 * The StateDefinition is used to describe the domain of the state, and the DeriveDefinition
 * sub-divides that domain into specific keys. These keys are used to cache data in memory and enables derived state to
 * be calculated once regardless of multiple execution contexts.
 */
class bw_DeriveDefinition {
    /**
     * Creates a new instance of a DeriveDefinition. Derived state is always stored in memory, so the storage location
     * defined in @link{StateDefinition} is ignored.
     *
     * @param stateDefinition The state definition for which this key belongs to.
     * @param uniqueDerivationName The name of the key, this should be unique per domain.
     * @param options A set of options to customize the behavior of {@link DeriveDefinition}.
     * @param options.derive A function to use to convert values from TFrom to TTo. This is called on each emit of the parent state observable
     * and the resulting value will be emitted from the derived state observable.
     * @param options.cleanupDelayMs The number of milliseconds to wait before cleaning up the state after the last subscriber has unsubscribed.
     * Defaults to 1000ms.
     * @param options.dependencyShape An object defining the dependencies of the derive function. The keys of the object are the names of the dependencies
     * and the values are the types of the dependencies.
     * for example:
     * ```
     * {
     *   myService: MyService,
     *   myOtherService: MyOtherService,
     * }
     * ```
     *
     * @param options.deserializer A function to use to safely convert your type from json to your expected type.
     *   Your data may be serialized/deserialized at any time and this needs callback needs to be able to faithfully re-initialize
     *   from the JSON object representation of your type.
     */
    constructor(stateDefinition, uniqueDerivationName, options) {
        this.stateDefinition = stateDefinition;
        this.uniqueDerivationName = uniqueDerivationName;
        this.options = options;
    }
    /**
     * Factory that produces a {@link DeriveDefinition} from a {@link KeyDefinition} or {@link DeriveDefinition} and new name.
     *
     * If a `KeyDefinition` is passed in, the returned definition will have the same key as the given key definition, but
     * will not collide with it in storage, even if they both reside in memory.
     *
     * If a `DeriveDefinition` is passed in, the returned definition will instead use the name given in the second position
     * of the tuple. It is up to you to ensure this is unique within the domain of derived state.
     *
     * @param options A set of options to customize the behavior of {@link DeriveDefinition}.
     * @param options.derive A function to use to convert values from TFrom to TTo. This is called on each emit of the parent state observable
     * and the resulting value will be emitted from the derived state observable.
     * @param options.cleanupDelayMs The number of milliseconds to wait before cleaning up the state after the last subscriber has unsubscribed.
     * Defaults to 1000ms.
     * @param options.dependencyShape An object defining the dependencies of the derive function. The keys of the object are the names of the dependencies
     * and the values are the types of the dependencies.
     * for example:
     * ```
     * {
     *   myService: MyService,
     *   myOtherService: MyOtherService,
     * }
     * ```
     *
     * @param options.deserializer A function to use to safely convert your type from json to your expected type.
     *   Your data may be serialized/deserialized at any time and this needs callback needs to be able to faithfully re-initialize
     *   from the JSON object representation of your type.
     * @param definition
     * @param options
     * @returns
     */
    static from(definition, options) {
        if (bw_isFromDeriveDefinition(definition)) {
            return new bw_DeriveDefinition(definition[0].stateDefinition, definition[1], options);
        }
        else {
            return new bw_DeriveDefinition(definition.stateDefinition, definition.key, options);
        }
    }
    static fromWithUserId(definition, options) {
        if (bw_isFromDeriveDefinition(definition)) {
            return new bw_DeriveDefinition(definition[0].stateDefinition, definition[1], options);
        }
        else {
            return new bw_DeriveDefinition(definition.stateDefinition, definition.key, options);
        }
    }
    get derive() {
        return this.options.derive;
    }
    deserialize(serialized) {
        return this.options.deserializer(serialized);
    }
    get cleanupDelayMs() {
        var _a;
        return this.options.cleanupDelayMs < 0 ? 0 : ((_a = this.options.cleanupDelayMs) !== null && _a !== void 0 ? _a : 1000);
    }
    get clearOnCleanup() {
        var _a;
        return (_a = this.options.clearOnCleanup) !== null && _a !== void 0 ? _a : true;
    }
    buildCacheKey() {
        return `derived_${this.stateDefinition.name}_${this.uniqueDerivationName}`;
    }
    /**
     * Creates a {@link StorageKey} that points to the data for the given derived definition.
     * @returns A key that is ready to be used in a storage service to get data.
     */
    get storageKey() {
        return `derived_${this.stateDefinition.name}_${this.uniqueDerivationName}`;
    }
}
function bw_isFromDeriveDefinition(definition) {
    return Array.isArray(definition);
}

;// ../../libs/common/src/platform/state/deserialization-helpers.ts
/**
 *
 * @param elementDeserializer
 * @returns
 */
function bw_array(elementDeserializer) {
    return (array) => {
        if (array == null) {
            return null;
        }
        return array.map((element) => elementDeserializer(element));
    };
}
/**
 *
 * @param valueDeserializer
 */
function bw_record(valueDeserializer) {
    return (jsonValue) => {
        if (jsonValue == null) {
            return null;
        }
        const output = {};
        Object.entries(jsonValue).forEach(([key, value]) => {
            output[key] = valueDeserializer(value);
        });
        return output;
    };
}

;// ../../libs/common/src/platform/state/key-definition.ts

/**
 * KeyDefinitions describe the precise location to store data for a given piece of state.
 * The StateDefinition is used to describe the domain of the state, and the KeyDefinition
 * sub-divides that domain into specific keys.
 */
class bw_KeyDefinition {
    /**
     * Creates a new instance of a KeyDefinition
     * @param stateDefinition The state definition for which this key belongs to.
     * @param key The name of the key, this should be unique per domain.
     * @param options A set of options to customize the behavior of {@link KeyDefinition}. All options are required.
     * @param options.deserializer A function to use to safely convert your type from json to your expected type.
     *   Your data may be serialized/deserialized at any time and this needs callback needs to be able to faithfully re-initialize
     *   from the JSON object representation of your type.
     */
    constructor(stateDefinition, key, options) {
        var _a;
        this.stateDefinition = stateDefinition;
        this.key = key;
        this.options = options;
        if (options.deserializer == null) {
            throw new Error(`'deserializer' is a required property on key ${this.errorKeyName}`);
        }
        if (options.cleanupDelayMs < 0) {
            throw new Error(`'cleanupDelayMs' must be greater than or equal to 0. Value of ${options.cleanupDelayMs} passed to key ${this.errorKeyName} `);
        }
        // Normalize optional debug options
        const { enableUpdateLogging = false, enableRetrievalLogging = false } = (_a = options.debug) !== null && _a !== void 0 ? _a : {};
        this.debug = {
            enableUpdateLogging,
            enableRetrievalLogging,
        };
    }
    /**
     * Gets the deserializer configured for this {@link KeyDefinition}
     */
    get deserializer() {
        return this.options.deserializer;
    }
    /**
     * Gets the number of milliseconds to wait before cleaning up the state after the last subscriber has unsubscribed.
     */
    get cleanupDelayMs() {
        var _a;
        return this.options.cleanupDelayMs < 0 ? 0 : ((_a = this.options.cleanupDelayMs) !== null && _a !== void 0 ? _a : 1000);
    }
    /**
     * Creates a {@link KeyDefinition} for state that is an array.
     * @param stateDefinition The state definition to be added to the KeyDefinition
     * @param key The key to be added to the KeyDefinition
     * @param options The options to customize the final {@link KeyDefinition}.
     * @returns A {@link KeyDefinition} initialized for arrays, the options run
     * the deserializer on the provided options for each element of an array.
     *
     * @example
     * ```typescript
     * const MY_KEY = KeyDefinition.array<MyArrayElement>(MY_STATE, "key", {
     *   deserializer: (myJsonElement) => convertToElement(myJsonElement),
     * });
     * ```
     */
    static array(stateDefinition, key, 
    // We have them provide options for the element of the array, depending on future options we add, this could get a little weird.
    options) {
        return new bw_KeyDefinition(stateDefinition, key, Object.assign(Object.assign({}, options), { deserializer: bw_array((e) => options.deserializer(e)) }));
    }
    /**
     * Creates a {@link KeyDefinition} for state that is a record.
     * @param stateDefinition The state definition to be added to the KeyDefinition
     * @param key The key to be added to the KeyDefinition
     * @param options The options to customize the final {@link KeyDefinition}.
     * @returns A {@link KeyDefinition} that contains a serializer that will run the provided deserializer for each
     * value in a record and returns every key as a string.
     *
     * @example
     * ```typescript
     * const MY_KEY = KeyDefinition.record<MyRecordValue>(MY_STATE, "key", {
     *   deserializer: (myJsonValue) => convertToValue(myJsonValue),
     * });
     * ```
     */
    static record(stateDefinition, key, 
    // We have them provide options for the value of the record, depending on future options we add, this could get a little weird.
    options) {
        return new bw_KeyDefinition(stateDefinition, key, Object.assign(Object.assign({}, options), { deserializer: bw_record((v) => options.deserializer(v)) }));
    }
    get fullName() {
        return `${this.stateDefinition.name}_${this.key}`;
    }
    get errorKeyName() {
        return `${this.stateDefinition.name} > ${this.key}`;
    }
}
/**
 * Creates a {@link StorageKey}
 * @param keyDefinition The key definition of which data the key should point to.
 * @returns A key that is ready to be used in a storage service to get data.
 */
function bw_globalKeyBuilder(keyDefinition) {
    return `global_${keyDefinition.stateDefinition.name}_${keyDefinition.key}`;
}

;// ../../libs/common/src/platform/state/user-key-definition.ts
var bw_a;


const bw_USER_KEY_DEFINITION_MARKER = Symbol("UserKeyDefinition");
class bw_UserKeyDefinition {
    constructor(stateDefinition, key, options) {
        var _b;
        this.stateDefinition = stateDefinition;
        this.key = key;
        this.options = options;
        this[bw_a] = true;
        if (options.deserializer == null) {
            throw new Error(`'deserializer' is a required property on key ${this.errorKeyName}`);
        }
        if (options.cleanupDelayMs < 0) {
            throw new Error(`'cleanupDelayMs' must be greater than or equal to 0. Value of ${options.cleanupDelayMs} passed to key ${this.errorKeyName} `);
        }
        // Filter out repeat values
        this.clearOn = Array.from(new Set(options.clearOn));
        // Normalize optional debug options
        const { enableUpdateLogging = false, enableRetrievalLogging = false } = (_b = options.debug) !== null && _b !== void 0 ? _b : {};
        this.debug = {
            enableUpdateLogging,
            enableRetrievalLogging,
        };
    }
    /**
     * Gets the deserializer configured for this {@link KeyDefinition}
     */
    get deserializer() {
        return this.options.deserializer;
    }
    /**
     * Gets the number of milliseconds to wait before cleaning up the state after the last subscriber has unsubscribed.
     */
    get cleanupDelayMs() {
        var _b;
        return this.options.cleanupDelayMs < 0 ? 0 : ((_b = this.options.cleanupDelayMs) !== null && _b !== void 0 ? _b : 1000);
    }
    /**
     * Creates a {@link UserKeyDefinition} for state that is an array.
     * @param stateDefinition The state definition to be added to the UserKeyDefinition
     * @param key The key to be added to the KeyDefinition
     * @param options The options to customize the final {@link UserKeyDefinition}.
     * @returns A {@link UserKeyDefinition} initialized for arrays, the options run
     * the deserializer on the provided options for each element of an array
     * **unless that array is null, in which case it will return an empty list.**
     *
     * @example
     * ```typescript
     * const MY_KEY = UserKeyDefinition.array<MyArrayElement>(MY_STATE, "key", {
     *   deserializer: (myJsonElement) => convertToElement(myJsonElement),
     * });
     * ```
     */
    static array(stateDefinition, key, 
    // We have them provide options for the element of the array, depending on future options we add, this could get a little weird.
    options) {
        return new bw_UserKeyDefinition(stateDefinition, key, Object.assign(Object.assign({}, options), { deserializer: bw_array((e) => options.deserializer(e)) }));
    }
    /**
     * Creates a {@link UserKeyDefinition} for state that is a record.
     * @param stateDefinition The state definition to be added to the UserKeyDefinition
     * @param key The key to be added to the KeyDefinition
     * @param options The options to customize the final {@link UserKeyDefinition}.
     * @returns A {@link UserKeyDefinition} that contains a serializer that will run the provided deserializer for each
     * value in a record and returns every key as a string **unless that record is null, in which case it will return an record.**
     *
     * @example
     * ```typescript
     * const MY_KEY = UserKeyDefinition.record<MyRecordValue>(MY_STATE, "key", {
     *   deserializer: (myJsonValue) => convertToValue(myJsonValue),
     * });
     * ```
     */
    static record(stateDefinition, key, 
    // We have them provide options for the value of the record, depending on future options we add, this could get a little weird.
    options) {
        return new bw_UserKeyDefinition(stateDefinition, key, Object.assign(Object.assign({}, options), { deserializer: bw_record((v) => options.deserializer(v)) }));
    }
    get fullName() {
        return `${this.stateDefinition.name}_${this.key}`;
    }
    buildKey(userId) {
        if (!bw_utils_Utils.isGuid(userId)) {
            throw new Error(`You cannot build a user key without a valid UserId, building for key ${this.fullName}`);
        }
        return `user_${userId}_${this.stateDefinition.name}_${this.key}`;
    }
    get errorKeyName() {
        return `${this.stateDefinition.name} > ${this.key}`;
    }
}
bw_a = bw_USER_KEY_DEFINITION_MARKER;

;// ../../libs/common/src/platform/state/state-definition.ts
/**
 * Defines the base location and instruction of where this state is expected to be located.
 */
class bw_StateDefinition {
    /**
     * Creates a new instance of {@link StateDefinition}, the creation of which is owned by the platform team.
     * @param name The name of the state, this needs to be unique from all other {@link StateDefinition}'s.
     * @param defaultStorageLocation The location of where this state should be stored.
     */
    constructor(name, defaultStorageLocation, storageLocationOverrides) {
        this.name = name;
        this.defaultStorageLocation = defaultStorageLocation;
        this.storageLocationOverrides = storageLocationOverrides !== null && storageLocationOverrides !== void 0 ? storageLocationOverrides : {};
    }
}

;// ../../libs/common/src/platform/state/state-definitions.ts

/**
 * `StateDefinition`s comes with some rules, to facilitate a quick review from
 * platform of this file, ensure you follow these rules, the ones marked with (tested)
 * have unit tests that you can run locally.
 *
 * 1. (tested) Names should not be null or undefined
 * 2. (tested) Name and storage location should be unique
 * 3. (tested) Name and storage location can't differ from another export by only casing
 * 4. (tested) Name should be longer than 3 characters. It should be descriptive, but brief.
 * 5. (tested) Name should not contain spaces or underscores
 * 6. Name should be human readable
 * 7. Name should be in camelCase format (unit tests ensure the first character is lowercase)
 * 8. Teams should only use state definitions they have created
 * 9. StateDefinitions should only be used for keys relating to the state name they chose
 *
 */
// Admin Console
const bw_ORGANIZATIONS_DISK = new bw_StateDefinition("organizations", "disk");
const bw_POLICIES_DISK = new bw_StateDefinition("policies", "disk");
const bw_PROVIDERS_DISK = new bw_StateDefinition("providers", "disk");
const bw_ORGANIZATION_MANAGEMENT_PREFERENCES_DISK = new bw_StateDefinition("organizationManagementPreferences", "disk", {
    web: "disk-local",
});
const bw_ACCOUNT_DEPROVISIONING_BANNER_DISK = new bw_StateDefinition("showAccountDeprovisioningBanner", "disk", {
    web: "disk-local",
});
const bw_DELETE_MANAGED_USER_WARNING = new bw_StateDefinition("showDeleteManagedUserWarning", "disk", {
    web: "disk-local",
});
// Billing
const bw_BILLING_DISK = new bw_StateDefinition("billing", "disk");
// Auth
const bw_ACCOUNT_DISK = new bw_StateDefinition("account", "disk");
const bw_ACCOUNT_MEMORY = new bw_StateDefinition("account", "memory");
const bw_AUTH_REQUEST_DISK_LOCAL = new bw_StateDefinition("authRequestLocal", "disk", {
    web: "disk-local",
});
const bw_AVATAR_DISK = new bw_StateDefinition("avatar", "disk", { web: "disk-local" });
const bw_DEVICE_TRUST_DISK_LOCAL = new bw_StateDefinition("deviceTrust", "disk", {
    web: "disk-local",
    browser: "disk-backup-local-storage",
});
const bw_KDF_CONFIG_DISK = new bw_StateDefinition("kdfConfig", "disk");
const bw_KEY_CONNECTOR_DISK = new bw_StateDefinition("keyConnector", "disk");
const bw_LOGIN_EMAIL_DISK = new bw_StateDefinition("loginEmail", "disk", {
    web: "disk-local",
});
const bw_LOGIN_EMAIL_MEMORY = new bw_StateDefinition("loginEmail", "memory");
const bw_LOGIN_STRATEGY_MEMORY = new bw_StateDefinition("loginStrategy", "memory");
const bw_MASTER_PASSWORD_DISK = new bw_StateDefinition("masterPassword", "disk");
const bw_MASTER_PASSWORD_MEMORY = new bw_StateDefinition("masterPassword", "memory");
const bw_PIN_DISK = new bw_StateDefinition("pinUnlock", "disk");
const bw_PIN_MEMORY = new bw_StateDefinition("pinUnlock", "memory");
const bw_ROUTER_DISK = new bw_StateDefinition("router", "disk");
const bw_SSO_DISK = new bw_StateDefinition("ssoLogin", "disk");
const bw_TOKEN_DISK = new bw_StateDefinition("token", "disk");
const bw_TOKEN_DISK_LOCAL = new bw_StateDefinition("tokenDiskLocal", "disk", {
    web: "disk-local",
});
const bw_TOKEN_MEMORY = new bw_StateDefinition("token", "memory");
const bw_TWO_FACTOR_MEMORY = new bw_StateDefinition("twoFactor", "memory");
const bw_USER_DECRYPTION_OPTIONS_DISK = new bw_StateDefinition("userDecryptionOptions", "disk");
const bw_ORGANIZATION_INVITE_DISK = new bw_StateDefinition("organizationInvite", "disk");
const bw_VAULT_TIMEOUT_SETTINGS_DISK_LOCAL = new bw_StateDefinition("vaultTimeoutSettings", "disk", {
    web: "disk-local",
});
// Autofill
const bw_BADGE_SETTINGS_DISK = new bw_StateDefinition("badgeSettings", "disk");
const bw_USER_NOTIFICATION_SETTINGS_DISK = new bw_StateDefinition("userNotificationSettings", "disk");
const bw_DOMAIN_SETTINGS_DISK = new bw_StateDefinition("domainSettings", "disk");
const bw_AUTOFILL_SETTINGS_DISK = new bw_StateDefinition("autofillSettings", "disk");
const bw_AUTOFILL_SETTINGS_DISK_LOCAL = new bw_StateDefinition("autofillSettingsLocal", "disk", {
    web: "disk-local",
});
// Components
const bw_NEW_WEB_LAYOUT_BANNER_DISK = new bw_StateDefinition("newWebLayoutBanner", "disk", {
    web: "disk-local",
});
// Platform
const bw_APPLICATION_ID_DISK = new bw_StateDefinition("applicationId", "disk", {
    web: "disk-local",
});
const bw_BIOMETRIC_SETTINGS_DISK = new bw_StateDefinition("biometricSettings", "disk");
const bw_CLEAR_EVENT_DISK = new bw_StateDefinition("clearEvent", "disk");
const bw_CONFIG_DISK = new bw_StateDefinition("config", "disk", {
    web: "disk-local",
});
const bw_CRYPTO_DISK = new bw_StateDefinition("crypto", "disk");
const bw_CRYPTO_MEMORY = new bw_StateDefinition("crypto", "memory");
const bw_DESKTOP_SETTINGS_DISK = new bw_StateDefinition("desktopSettings", "disk");
const bw_ENVIRONMENT_DISK = new bw_StateDefinition("environment", "disk");
const bw_ENVIRONMENT_MEMORY = new bw_StateDefinition("environment", "memory");
const bw_POPUP_VIEW_MEMORY = new bw_StateDefinition("popupView", "memory", {
    browser: "memory-large-object",
});
const bw_SYNC_DISK = new bw_StateDefinition("sync", "disk", { web: "memory" });
const bw_THEMING_DISK = new bw_StateDefinition("theming", "disk", { web: "disk-local" });
const bw_TRANSLATION_DISK = new bw_StateDefinition("translation", "disk", { web: "disk-local" });
const bw_ANIMATION_DISK = new bw_StateDefinition("animation", "disk");
const bw_TASK_SCHEDULER_DISK = new bw_StateDefinition("taskScheduler", "disk");
const bw_EXTENSION_INITIAL_INSTALL_DISK = new bw_StateDefinition("extensionInitialInstall", "disk");
// Design System
const bw_POPUP_STYLE_DISK = new bw_StateDefinition("popupStyle", "disk");
// Secrets Manager
const bw_SM_ONBOARDING_DISK = new bw_StateDefinition("smOnboarding", "disk", {
    web: "disk-local",
});
// Tools
const bw_EXTENSION_DISK = new bw_StateDefinition("extension", "disk");
const bw_GENERATOR_DISK = new bw_StateDefinition("generator", "disk");
const bw_GENERATOR_MEMORY = new bw_StateDefinition("generator", "memory");
const bw_BROWSER_SEND_MEMORY = new bw_StateDefinition("sendBrowser", "memory");
const bw_EVENT_COLLECTION_DISK = new bw_StateDefinition("eventCollection", "disk");
const bw_SEND_DISK = new bw_StateDefinition("encryptedSend", "disk", {
    web: "memory",
});
const bw_SEND_MEMORY = new bw_StateDefinition("decryptedSend", "memory", {
    browser: "memory-large-object",
});
// Vault
const bw_COLLECTION_DATA = new bw_StateDefinition("collection", "disk", {
    web: "memory",
});
const bw_FOLDER_DISK = new bw_StateDefinition("folder", "disk", { web: "memory" });
const bw_FOLDER_MEMORY = new bw_StateDefinition("decryptedFolders", "memory", {
    browser: "memory-large-object",
});
const bw_VAULT_FILTER_DISK = new bw_StateDefinition("vaultFilter", "disk", {
    web: "disk-local",
});
const bw_VAULT_ONBOARDING = new bw_StateDefinition("vaultOnboarding", "disk", {
    web: "disk-local",
});
const bw_VAULT_SETTINGS_DISK = new bw_StateDefinition("vaultSettings", "disk", {
    web: "disk-local",
});
const bw_VAULT_BROWSER_MEMORY = new bw_StateDefinition("vaultBrowser", "memory", {
    browser: "memory-large-object",
});
const bw_VAULT_SEARCH_MEMORY = new bw_StateDefinition("vaultSearch", "memory", {
    browser: "memory-large-object",
});
const bw_CIPHERS_DISK = new bw_StateDefinition("ciphers", "disk", { web: "memory" });
const bw_CIPHERS_DISK_LOCAL = new bw_StateDefinition("ciphersLocal", "disk", {
    web: "disk-local",
});
const bw_CIPHERS_MEMORY = new bw_StateDefinition("ciphersMemory", "memory", {
    browser: "memory-large-object",
});
const bw_PREMIUM_BANNER_DISK_LOCAL = new bw_StateDefinition("premiumBannerReprompt", "disk", {
    web: "disk-local",
});
const bw_BANNERS_DISMISSED_DISK = new bw_StateDefinition("bannersDismissed", "disk");
const bw_NEW_DEVICE_VERIFICATION_NOTICE = new bw_StateDefinition("newDeviceVerificationNotice", "disk", {
    web: "disk-local",
});
const bw_VAULT_APPEARANCE = new bw_StateDefinition("vaultAppearance", "disk");
const bw_SECURITY_TASKS_DISK = new bw_StateDefinition("securityTasks", "disk");
const bw_AT_RISK_PASSWORDS_PAGE_DISK = new bw_StateDefinition("atRiskPasswordsPage", "disk");
const bw_NOTIFICATION_DISK = new bw_StateDefinition("notifications", "disk");

;// ../../libs/common/src/platform/state/state-event-registrar.service.ts
var bw_state_event_registrar_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


const bw_STATE_LOCK_EVENT = bw_KeyDefinition.array(bw_CLEAR_EVENT_DISK, "lock", {
    deserializer: (e) => e,
});
const bw_STATE_LOGOUT_EVENT = bw_KeyDefinition.array(bw_CLEAR_EVENT_DISK, "logout", {
    deserializer: (e) => e,
});
class bw_StateEventRegistrarService {
    constructor(globalStateProvider, storageServiceProvider) {
        this.storageServiceProvider = storageServiceProvider;
        this.stateEventStateMap = {
            lock: globalStateProvider.get(bw_STATE_LOCK_EVENT),
            logout: globalStateProvider.get(bw_STATE_LOGOUT_EVENT),
        };
    }
    registerEvents(keyDefinition) {
        return bw_state_event_registrar_service_awaiter(this, void 0, void 0, function* () {
            for (const clearEvent of keyDefinition.clearOn) {
                const eventState = this.stateEventStateMap[clearEvent];
                // Determine the storage location for this
                const [storageLocation] = this.storageServiceProvider.get(keyDefinition.stateDefinition.defaultStorageLocation, keyDefinition.stateDefinition.storageLocationOverrides);
                const newEvent = {
                    state: keyDefinition.stateDefinition.name,
                    key: keyDefinition.key,
                    location: storageLocation,
                };
                // Only update the event state if the existing list doesn't have a matching entry
                yield eventState.update((existingTickets) => {
                    existingTickets !== null && existingTickets !== void 0 ? existingTickets : (existingTickets = []);
                    existingTickets.push(newEvent);
                    return existingTickets;
                }, {
                    shouldUpdate: (currentTickets) => {
                        return (
                        // If the current tickets are null, then it will for sure be added
                        currentTickets == null ||
                            // If an existing match couldn't be found, we also need to add one
                            currentTickets.findIndex((e) => e.state === newEvent.state &&
                                e.key === newEvent.key &&
                                e.location === newEvent.location) === -1);
                    },
                });
            }
        });
    }
}

;// ../../libs/common/src/platform/state/state-event-runner.service.ts
var bw_state_event_runner_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_StateEventRunnerService {
    constructor(globalStateProvider, storageServiceProvider) {
        this.storageServiceProvider = storageServiceProvider;
        this.stateEventMap = {
            lock: globalStateProvider.get(bw_STATE_LOCK_EVENT),
            logout: globalStateProvider.get(bw_STATE_LOGOUT_EVENT),
        };
    }
    handleEvent(event, userId) {
        return bw_state_event_runner_service_awaiter(this, void 0, void 0, function* () {
            let tickets = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateEventMap[event].state$);
            tickets !== null && tickets !== void 0 ? tickets : (tickets = []);
            const failures = [];
            for (const ticket of tickets) {
                try {
                    const [, service] = this.storageServiceProvider.get(ticket.location, {});
                    const ticketStorageKey = this.storageKeyFor(userId, ticket);
                    // Evaluate current value so we can avoid writing to state if we don't need to
                    const currentValue = yield service.get(ticketStorageKey);
                    if (currentValue != null) {
                        yield service.remove(ticketStorageKey);
                    }
                }
                catch (err) {
                    let errorMessage = "Unknown Error";
                    if (typeof err === "object" && "message" in err && typeof err.message === "string") {
                        errorMessage = err.message;
                    }
                    failures.push(`${errorMessage} in ${ticket.state} > ${ticket.key} located ${ticket.location}`);
                }
            }
            if (failures.length > 0) {
                // Throw aggregated error
                throw new Error(`One or more errors occurred while handling event '${event}' for user ${userId}.\n${failures.join("\n")}`);
            }
        });
    }
    storageKeyFor(userId, ticket) {
        const userKey = new bw_UserKeyDefinition(new bw_StateDefinition(ticket.state, ticket.location), ticket.key, {
            deserializer: (v) => v,
            clearOn: [],
        });
        return userKey.buildKey(userId);
    }
}

;// ../../libs/common/src/platform/state/index.ts










;// ../../libs/auth/src/common/services/pin/pin.service.implementation.ts
var bw_pin_service_implementation_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




/**
 * The persistent (stored on disk) version of the UserKey, encrypted by the PinKey.
 *
 * @remarks Persists through a client reset. Used when `requireMasterPasswordOnClientRestart` is disabled.
 * @see SetPinComponent.setPinForm.requireMasterPasswordOnClientRestart
 */
const bw_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT = new bw_UserKeyDefinition(bw_PIN_DISK, "pinKeyEncryptedUserKeyPersistent", {
    deserializer: (jsonValue) => jsonValue,
    clearOn: ["logout"],
});
/**
 * The ephemeral (stored in memory) version of the UserKey, encrypted by the PinKey.
 *
 * @remarks Does NOT persist through a client reset. Used when `requireMasterPasswordOnClientRestart` is enabled.
 * @see SetPinComponent.setPinForm.requireMasterPasswordOnClientRestart
 */
const bw_PIN_KEY_ENCRYPTED_USER_KEY_EPHEMERAL = new bw_UserKeyDefinition(bw_PIN_MEMORY, "pinKeyEncryptedUserKeyEphemeral", {
    deserializer: (jsonValue) => jsonValue,
    clearOn: ["logout"],
});
/**
 * The PIN, encrypted by the UserKey.
 */
const bw_USER_KEY_ENCRYPTED_PIN = new bw_UserKeyDefinition(bw_PIN_DISK, "userKeyEncryptedPin", {
    deserializer: (jsonValue) => jsonValue,
    clearOn: ["logout"],
});
/**
 * The old MasterKey, encrypted by the PinKey (formerly called `pinProtected`).
 * Deprecated and used for migration purposes only.
 */
const bw_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY = new bw_UserKeyDefinition(bw_PIN_DISK, "oldPinKeyEncryptedMasterKey", {
    deserializer: (jsonValue) => jsonValue,
    clearOn: ["logout"],
});
class bw_PinService {
    constructor(accountService, cryptoFunctionService, encryptService, kdfConfigService, keyGenerationService, logService, masterPasswordService, stateProvider, stateService) {
        this.accountService = accountService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.encryptService = encryptService;
        this.kdfConfigService = kdfConfigService;
        this.keyGenerationService = keyGenerationService;
        this.logService = logService;
        this.masterPasswordService = masterPasswordService;
        this.stateProvider = stateProvider;
        this.stateService = stateService;
    }
    getPinKeyEncryptedUserKeyPersistent(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot get pinKeyEncryptedUserKeyPersistent.");
            return bw_enc_string_EncString.fromJSON(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT, userId)));
        });
    }
    /**
     * Sets the persistent (stored on disk) version of the UserKey, encrypted by the PinKey.
     */
    setPinKeyEncryptedUserKeyPersistent(pinKeyEncryptedUserKey, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot set pinKeyEncryptedUserKeyPersistent.");
            if (pinKeyEncryptedUserKey == null) {
                throw new Error("No pinKeyEncryptedUserKey provided. Cannot set pinKeyEncryptedUserKeyPersistent.");
            }
            yield this.stateProvider.setUserState(bw_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT, pinKeyEncryptedUserKey === null || pinKeyEncryptedUserKey === void 0 ? void 0 : pinKeyEncryptedUserKey.encryptedString, userId);
        });
    }
    clearPinKeyEncryptedUserKeyPersistent(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot clear pinKeyEncryptedUserKeyPersistent.");
            yield this.stateProvider.setUserState(bw_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT, null, userId);
        });
    }
    getPinKeyEncryptedUserKeyEphemeral(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot get pinKeyEncryptedUserKeyEphemeral.");
            return bw_enc_string_EncString.fromJSON(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_PIN_KEY_ENCRYPTED_USER_KEY_EPHEMERAL, userId)));
        });
    }
    /**
     * Sets the ephemeral (stored in memory) version of the UserKey, encrypted by the PinKey.
     */
    setPinKeyEncryptedUserKeyEphemeral(pinKeyEncryptedUserKey, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot set pinKeyEncryptedUserKeyEphemeral.");
            if (pinKeyEncryptedUserKey == null) {
                throw new Error("No pinKeyEncryptedUserKey provided. Cannot set pinKeyEncryptedUserKeyEphemeral.");
            }
            yield this.stateProvider.setUserState(bw_PIN_KEY_ENCRYPTED_USER_KEY_EPHEMERAL, pinKeyEncryptedUserKey === null || pinKeyEncryptedUserKey === void 0 ? void 0 : pinKeyEncryptedUserKey.encryptedString, userId);
        });
    }
    clearPinKeyEncryptedUserKeyEphemeral(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot clear pinKeyEncryptedUserKeyEphemeral.");
            yield this.stateProvider.setUserState(bw_PIN_KEY_ENCRYPTED_USER_KEY_EPHEMERAL, null, userId);
        });
    }
    createPinKeyEncryptedUserKey(pin, userKey, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot create pinKeyEncryptedUserKey.");
            if (!userKey) {
                throw new Error("No UserKey provided. Cannot create pinKeyEncryptedUserKey.");
            }
            const email = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.accounts$.pipe((0,bw_external_rxjs_namespaceObject.map)((accounts) => accounts[userId].email)));
            const kdfConfig = yield this.kdfConfigService.getKdfConfig();
            const pinKey = yield this.makePinKey(pin, email, kdfConfig);
            return yield this.encryptService.encrypt(userKey.key, pinKey);
        });
    }
    storePinKeyEncryptedUserKey(pinKeyEncryptedUserKey, storeAsEphemeral, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot store pinKeyEncryptedUserKey.");
            if (storeAsEphemeral) {
                yield this.setPinKeyEncryptedUserKeyEphemeral(pinKeyEncryptedUserKey, userId);
            }
            else {
                yield this.setPinKeyEncryptedUserKeyPersistent(pinKeyEncryptedUserKey, userId);
            }
        });
    }
    getUserKeyEncryptedPin(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot get userKeyEncryptedPin.");
            return bw_enc_string_EncString.fromJSON(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_USER_KEY_ENCRYPTED_PIN, userId)));
        });
    }
    setUserKeyEncryptedPin(userKeyEncryptedPin, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot set userKeyEncryptedPin.");
            yield this.stateProvider.setUserState(bw_USER_KEY_ENCRYPTED_PIN, userKeyEncryptedPin === null || userKeyEncryptedPin === void 0 ? void 0 : userKeyEncryptedPin.encryptedString, userId);
        });
    }
    clearUserKeyEncryptedPin(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot clear userKeyEncryptedPin.");
            yield this.stateProvider.setUserState(bw_USER_KEY_ENCRYPTED_PIN, null, userId);
        });
    }
    createUserKeyEncryptedPin(pin, userKey) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userKey) {
                throw new Error("No UserKey provided. Cannot create userKeyEncryptedPin.");
            }
            return yield this.encryptService.encrypt(pin, userKey);
        });
    }
    getOldPinKeyEncryptedMasterKey(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot get oldPinKeyEncryptedMasterKey.");
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY, userId));
        });
    }
    clearOldPinKeyEncryptedMasterKey(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot clear oldPinKeyEncryptedMasterKey.");
            yield this.stateProvider.setUserState(bw_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY, null, userId);
        });
    }
    makePinKey(pin, salt, kdfConfig) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            const pinKey = yield this.keyGenerationService.deriveKeyFromPassword(pin, salt, kdfConfig);
            return (yield this.keyGenerationService.stretchKey(pinKey));
        });
    }
    getPinLockType(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot get PinLockType.");
            /**
             * We can't check the `userKeyEncryptedPin` (formerly called `protectedPin`) for both because old
             * accounts only used it for MP on Restart
             */
            const aUserKeyEncryptedPinIsSet = !!(yield this.getUserKeyEncryptedPin(userId));
            const aPinKeyEncryptedUserKeyPersistentIsSet = !!(yield this.getPinKeyEncryptedUserKeyPersistent(userId));
            const anOldPinKeyEncryptedMasterKeyIsSet = !!(yield this.getOldPinKeyEncryptedMasterKey(userId));
            if (aPinKeyEncryptedUserKeyPersistentIsSet || anOldPinKeyEncryptedMasterKeyIsSet) {
                return "PERSISTENT";
            }
            else if (aUserKeyEncryptedPinIsSet &&
                !aPinKeyEncryptedUserKeyPersistentIsSet &&
                !anOldPinKeyEncryptedMasterKeyIsSet) {
                return "EPHEMERAL";
            }
            else {
                return "DISABLED";
            }
        });
    }
    isPinSet(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot determine if PIN is set.");
            return (yield this.getPinLockType(userId)) !== "DISABLED";
        });
    }
    isPinDecryptionAvailable(userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot determine if decryption of user key via PIN is available.");
            const pinLockType = yield this.getPinLockType(userId);
            switch (pinLockType) {
                case "DISABLED":
                    return false;
                case "PERSISTENT":
                    // The above getPinLockType call ensures that we have either a PinKeyEncryptedUserKey or OldPinKeyEncryptedMasterKey set.
                    return true;
                case "EPHEMERAL": {
                    // The above getPinLockType call ensures that we have a UserKeyEncryptedPin set.
                    // However, we must additively check to ensure that we have a set PinKeyEncryptedUserKeyEphemeral b/c otherwise
                    // we cannot take a PIN, derive a PIN key, and decrypt the ephemeral UserKey.
                    const pinKeyEncryptedUserKeyEphemeral = yield this.getPinKeyEncryptedUserKeyEphemeral(userId);
                    return Boolean(pinKeyEncryptedUserKeyEphemeral);
                }
                default: {
                    // Compile-time check for exhaustive switch
                    const _exhaustiveCheck = pinLockType;
                    throw new Error(`Unexpected pinLockType: ${_exhaustiveCheck}`);
                }
            }
        });
    }
    decryptUserKeyWithPin(pin, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot decrypt user key with PIN.");
            try {
                const pinLockType = yield this.getPinLockType(userId);
                const requireMasterPasswordOnClientRestart = pinLockType === "EPHEMERAL";
                const { pinKeyEncryptedUserKey, oldPinKeyEncryptedMasterKey } = yield this.getPinKeyEncryptedKeys(pinLockType, userId);
                const email = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.accounts$.pipe((0,bw_external_rxjs_namespaceObject.map)((accounts) => accounts[userId].email)));
                const kdfConfig = yield this.kdfConfigService.getKdfConfig();
                let userKey;
                if (oldPinKeyEncryptedMasterKey) {
                    userKey = yield this.decryptAndMigrateOldPinKeyEncryptedMasterKey(userId, pin, email, kdfConfig, requireMasterPasswordOnClientRestart, oldPinKeyEncryptedMasterKey);
                }
                else {
                    userKey = yield this.decryptUserKey(userId, pin, email, kdfConfig, pinKeyEncryptedUserKey);
                }
                if (!userKey) {
                    this.logService.warning(`User key null after pin key decryption.`);
                    return null;
                }
                if (!(yield this.validatePin(userKey, pin, userId))) {
                    this.logService.warning(`Pin key decryption successful but pin validation failed.`);
                    return null;
                }
                return userKey;
            }
            catch (error) {
                this.logService.error(`Error decrypting user key with pin: ${error}`);
                return null;
            }
        });
    }
    /**
     * Decrypts the UserKey with the provided PIN.
     */
    decryptUserKey(userId, pin, salt, kdfConfig, pinKeyEncryptedUserKey) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot decrypt user key.");
            pinKeyEncryptedUserKey || (pinKeyEncryptedUserKey = yield this.getPinKeyEncryptedUserKeyPersistent(userId));
            pinKeyEncryptedUserKey || (pinKeyEncryptedUserKey = yield this.getPinKeyEncryptedUserKeyEphemeral(userId));
            if (!pinKeyEncryptedUserKey) {
                throw new Error("No pinKeyEncryptedUserKey found.");
            }
            const pinKey = yield this.makePinKey(pin, salt, kdfConfig);
            const userKey = yield this.encryptService.decryptToBytes(pinKeyEncryptedUserKey, pinKey);
            return new bw_SymmetricCryptoKey(userKey);
        });
    }
    /**
     * Creates a new `pinKeyEncryptedUserKey` and clears the `oldPinKeyEncryptedMasterKey`.
     * @returns UserKey
     */
    decryptAndMigrateOldPinKeyEncryptedMasterKey(userId, pin, email, kdfConfig, requireMasterPasswordOnClientRestart, oldPinKeyEncryptedMasterKey) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot decrypt and migrate oldPinKeyEncryptedMasterKey.");
            const masterKey = yield this.decryptMasterKeyWithPin(userId, pin, email, kdfConfig, oldPinKeyEncryptedMasterKey);
            const encUserKey = yield this.stateService.getEncryptedCryptoSymmetricKey({ userId: userId });
            const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId, encUserKey ? new bw_enc_string_EncString(encUserKey) : undefined);
            const pinKeyEncryptedUserKey = yield this.createPinKeyEncryptedUserKey(pin, userKey, userId);
            yield this.storePinKeyEncryptedUserKey(pinKeyEncryptedUserKey, requireMasterPasswordOnClientRestart, userId);
            const userKeyEncryptedPin = yield this.createUserKeyEncryptedPin(pin, userKey);
            yield this.setUserKeyEncryptedPin(userKeyEncryptedPin, userId);
            yield this.clearOldPinKeyEncryptedMasterKey(userId);
            return userKey;
        });
    }
    // Only for migration purposes
    decryptMasterKeyWithPin(userId, pin, salt, kdfConfig, oldPinKeyEncryptedMasterKey) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot decrypt master key with PIN.");
            if (!oldPinKeyEncryptedMasterKey) {
                const oldPinKeyEncryptedMasterKeyString = yield this.getOldPinKeyEncryptedMasterKey(userId);
                if (oldPinKeyEncryptedMasterKeyString == null) {
                    throw new Error("No oldPinKeyEncrytedMasterKey found.");
                }
                oldPinKeyEncryptedMasterKey = new bw_enc_string_EncString(oldPinKeyEncryptedMasterKeyString);
            }
            const pinKey = yield this.makePinKey(pin, salt, kdfConfig);
            const masterKey = yield this.encryptService.decryptToBytes(oldPinKeyEncryptedMasterKey, pinKey);
            return new bw_SymmetricCryptoKey(masterKey);
        });
    }
    /**
     * Gets the user's `pinKeyEncryptedUserKey` (persistent or ephemeral) and `oldPinKeyEncryptedMasterKey`
     * (if one exists) based on the user's PinLockType.
     *
     * @remarks The `oldPinKeyEncryptedMasterKey` (formerly `pinProtected`) is only used for migration and
     *          will be null for all migrated accounts.
     * @throws If PinLockType is 'DISABLED' or if userId is not provided
     */
    getPinKeyEncryptedKeys(pinLockType, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot get PinKey encrypted keys.");
            switch (pinLockType) {
                case "PERSISTENT": {
                    const pinKeyEncryptedUserKey = yield this.getPinKeyEncryptedUserKeyPersistent(userId);
                    const oldPinKeyEncryptedMasterKey = yield this.getOldPinKeyEncryptedMasterKey(userId);
                    return {
                        pinKeyEncryptedUserKey,
                        oldPinKeyEncryptedMasterKey: oldPinKeyEncryptedMasterKey
                            ? new bw_enc_string_EncString(oldPinKeyEncryptedMasterKey)
                            : undefined,
                    };
                }
                case "EPHEMERAL": {
                    const pinKeyEncryptedUserKey = yield this.getPinKeyEncryptedUserKeyEphemeral(userId);
                    return {
                        pinKeyEncryptedUserKey,
                        oldPinKeyEncryptedMasterKey: undefined, // Going forward, we only migrate non-ephemeral version
                    };
                }
                case "DISABLED":
                    throw new Error("Pin is disabled");
                default: {
                    // Compile-time check for exhaustive switch
                    const _exhaustiveCheck = pinLockType;
                    return _exhaustiveCheck;
                }
            }
        });
    }
    validatePin(userKey, pin, userId) {
        return bw_pin_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.validateUserId(userId, "Cannot validate PIN.");
            const userKeyEncryptedPin = yield this.getUserKeyEncryptedPin(userId);
            const decryptedPin = yield this.encryptService.decryptToUtf8(userKeyEncryptedPin, userKey);
            const isPinValid = this.cryptoFunctionService.compareFast(decryptedPin, pin);
            return isPinValid;
        });
    }
    /**
     * Throws a custom error message if user ID is not provided.
     */
    validateUserId(userId, errorMessage = "") {
        if (!userId) {
            throw new Error(`User ID is required. ${errorMessage}`);
        }
    }
}

;// ../../libs/auth/src/common/services/login-email/login-email.service.ts
var bw_login_email_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


// FIXME: remove `src` and fix import
// eslint-disable-next-line no-restricted-imports

const bw_LOGIN_EMAIL = new bw_KeyDefinition(bw_LOGIN_EMAIL_MEMORY, "loginEmail", {
    deserializer: (value) => value,
});
const bw_STORED_EMAIL = new bw_KeyDefinition(bw_LOGIN_EMAIL_DISK, "storedEmail", {
    deserializer: (value) => value,
});
class bw_LoginEmailService {
    constructor(accountService, authService, stateProvider) {
        this.accountService = accountService;
        this.authService = authService;
        this.stateProvider = stateProvider;
        this.loginEmailState = this.stateProvider.getGlobal(bw_LOGIN_EMAIL);
        this.storedEmailState = this.stateProvider.getGlobal(bw_STORED_EMAIL);
        // In order to determine if an account is being added, we check if any account is not logged out
        this.addingAccount$ = this.authService.authStatuses$.pipe(switchMap((statuses) => bw_login_email_service_awaiter(this, void 0, void 0, function* () {
            // We don't want to consider the active account since it may have just changed auth status to logged in
            // which would make this observable think an account is being added
            const activeUser = yield firstValueFrom(this.accountService.activeAccount$);
            if (activeUser) {
                delete statuses[activeUser.id];
            }
            return Object.values(statuses).some((status) => status !== AuthenticationStatus.LoggedOut);
        })));
        this.loginEmail$ = this.loginEmailState.state$;
        this.storedEmail$ = this.storedEmailState.state$.pipe(switchMap((storedEmail) => bw_login_email_service_awaiter(this, void 0, void 0, function* () {
            // When adding an account, we don't show the stored email
            if (yield firstValueFrom(this.addingAccount$)) {
                return null;
            }
            return storedEmail;
        })));
    }
    setLoginEmail(email) {
        return bw_login_email_service_awaiter(this, void 0, void 0, function* () {
            yield this.loginEmailState.update((_) => email);
        });
    }
    getRememberEmail() {
        return this.rememberEmail;
    }
    setRememberEmail(value) {
        this.rememberEmail = value !== null && value !== void 0 ? value : false;
    }
    // Note: only clear values on successful login or you are sure they are not needed.
    // Browser uses these values to maintain the email between login and 2fa components so
    // we do not want to clear them too early.
    clearValues() {
        return bw_login_email_service_awaiter(this, void 0, void 0, function* () {
            yield this.setLoginEmail(null);
            this.rememberEmail = false;
        });
    }
    saveEmailSettings() {
        return bw_login_email_service_awaiter(this, void 0, void 0, function* () {
            const addingAccount = yield firstValueFrom(this.addingAccount$);
            const email = yield firstValueFrom(this.loginEmail$);
            yield this.storedEmailState.update((storedEmail) => {
                // If we're adding an account, only overwrite the stored email when rememberEmail is true
                if (addingAccount) {
                    if (this.rememberEmail) {
                        return email;
                    }
                    return storedEmail;
                }
                // Saving with rememberEmail set to false will clear the stored email
                if (this.rememberEmail) {
                    return email;
                }
                return null;
            });
        });
    }
}

;// ../../libs/common/src/models/request/prelogin.request.ts
class bw_PreloginRequest {
    constructor(email) {
        this.email = email;
    }
}

;// ../../libs/common/src/platform/scheduling/task-scheduler.service.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/**
 * Creates a RXJS scheduler based on a {@link TaskSchedulerService}.
 *
 * @description This API defers to `TaskSchedulerService` to schedule a task to be ran
 * in the future but the task that is ran is NOT the remainder of your RXJS pipeline. The
 * task you want ran must instead be registered in a location reachable on a service worker
 * startup (on browser). An example of an acceptible location is the constructor of a service
 * you know is created in `MainBackground`. Uses of this API is other clients _can_ have the
 * `registerTaskHandler` call in more places, but in order to have it work across clients
 * it is recommended to register it according to the rules of browser.
 *
 * @link https://rxjs.dev/guide/scheduler#using-schedulers
 *
 * @example
 * ```ts
 * class MyService {
 *   constructor(messageListener: MessageListener, taskScheduler: TaskSchedulerService) {
 *    // VERY IMPORTANT!
 *    this.taskSchedulerService.registerTaskHandler(SchedulerTaskNames.myTaskName, async () => {
 *      await this.runEvent();
 *    });
 *
 *     messageListener.messages$(MY_MESSAGE).pipe(
 *        debounceTime(
 *          10 * 1000,
 *          toScheduler(taskScheduler, ShedulerTaskNames.myTaskName),
 *        ),
 *        switchMap(() => this.runEvent()),
 *     )
 *   }
 * }
 * ```
 *
 * @param taskScheduler The task scheduler service to use to shedule RXJS work.
 * @param taskName The name of the task that the handler should be registered and scheduled based on.
 * @returns A SchedulerLike object that can be passed in to RXJS operators like `delay` and `timeout`.
 */
function bw_toScheduler(taskScheduler, taskName) {
    return new bw_TaskSchedulerSheduler(taskScheduler, taskName);
}
class bw_TaskSchedulerSheduler {
    constructor(taskSchedulerService, taskName) {
        this.taskSchedulerService = taskSchedulerService;
        this.taskName = taskName;
    }
    schedule(work, delay, state) {
        return this.taskSchedulerService.setTimeout(this.taskName, delay !== null && delay !== void 0 ? delay : 0);
    }
    now() {
        return asyncScheduler.now();
    }
}
class bw_TaskSchedulerService {
}

;// ../../libs/common/src/platform/scheduling/default-task-scheduler.service.ts
var bw_default_task_scheduler_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_DefaultTaskSchedulerService extends bw_TaskSchedulerService {
    constructor(logService) {
        super();
        this.logService = logService;
        this.taskHandlers = new Map();
    }
    /**
     * Sets a timeout and returns the timeout id.
     *
     * @param taskName - The name of the task. Unused in the base implementation.
     * @param delayInMs - The delay in milliseconds.
     */
    setTimeout(taskName, delayInMs) {
        this.validateRegisteredTask(taskName);
        const timeoutHandle = globalThis.setTimeout(() => this.triggerTask(taskName), delayInMs);
        return new bw_external_rxjs_namespaceObject.Subscription(() => globalThis.clearTimeout(timeoutHandle));
    }
    /**
     * Sets an interval and returns the interval id.
     *
     * @param taskName - The name of the task. Unused in the base implementation.
     * @param intervalInMs - The interval in milliseconds.
     * @param _initialDelayInMs - The initial delay in milliseconds. Unused in the base implementation.
     */
    setInterval(taskName, intervalInMs, _initialDelayInMs) {
        this.validateRegisteredTask(taskName);
        const intervalHandle = globalThis.setInterval(() => this.triggerTask(taskName), intervalInMs);
        return new bw_external_rxjs_namespaceObject.Subscription(() => globalThis.clearInterval(intervalHandle));
    }
    /**
     * Registers a task handler.
     *
     * @param taskName - The name of the task.
     * @param handler - The task handler.
     */
    registerTaskHandler(taskName, handler) {
        const existingHandler = this.taskHandlers.get(taskName);
        if (existingHandler) {
            this.logService.warning(`Task handler for ${taskName} already exists. Overwriting.`);
            this.unregisterTaskHandler(taskName);
        }
        this.taskHandlers.set(taskName, handler);
    }
    /**
     * Unregisters a task handler.
     *
     * @param taskName - The name of the task.
     */
    unregisterTaskHandler(taskName) {
        this.taskHandlers.delete(taskName);
    }
    /**
     * Triggers a task.
     *
     * @param taskName - The name of the task.
     * @param _periodInMinutes - The period in minutes. Unused in the base implementation.
     */
    triggerTask(taskName, _periodInMinutes) {
        return bw_default_task_scheduler_service_awaiter(this, void 0, void 0, function* () {
            const handler = this.taskHandlers.get(taskName);
            if (handler) {
                handler();
            }
        });
    }
    /**
     * Validates that a task handler is registered.
     *
     * @param taskName - The name of the task.
     */
    validateRegisteredTask(taskName) {
        if (!this.taskHandlers.has(taskName)) {
            throw new Error(`Task handler for ${taskName} not registered. Unable to schedule task.`);
        }
    }
}

;// ../../libs/common/src/platform/scheduling/scheduled-task-name.enum.ts
const bw_ScheduledTaskNames = {
    generatePasswordClearClipboardTimeout: "generatePasswordClearClipboardTimeout",
    systemClearClipboardTimeout: "systemClearClipboardTimeout",
    loginStrategySessionTimeout: "loginStrategySessionTimeout",
    notificationsReconnectTimeout: "notificationsReconnectTimeout",
    fido2ClientAbortTimeout: "fido2ClientAbortTimeout",
    scheduleNextSyncInterval: "scheduleNextSyncInterval",
    eventUploadsInterval: "eventUploadsInterval",
    vaultTimeoutCheckInterval: "vaultTimeoutCheckInterval",
    clearPopupViewCache: "clearPopupViewCache",
};

;// ../../libs/common/src/platform/scheduling/index.ts




;// ../../libs/key-management/src/biometrics/biometric.state.ts

/**
 * Indicates whether the user elected to store a biometric key to unlock their vault.
 */
const bw_BIOMETRIC_UNLOCK_ENABLED = new bw_UserKeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "biometricUnlockEnabled", {
    deserializer: (obj) => obj,
    clearOn: [],
});
/**
 * Boolean indicating the user has elected to require a password to use their biometric key upon starting the application.
 *
 * A true setting controls whether {@link ENCRYPTED_CLIENT_KEY_HALF} is set.
 */
const bw_REQUIRE_PASSWORD_ON_START = new bw_UserKeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "requirePasswordOnStart", {
    deserializer: (value) => value,
    clearOn: [],
});
/**
 * If the user has elected to require a password on first unlock of an application instance, this key will store the
 * encrypted client key half used to unlock the vault.
 *
 * For operating systems without application-level key storage, this key half is concatenated with a signature
 * provided by the OS and used to encrypt the biometric key prior to storage.
 */
const bw_ENCRYPTED_CLIENT_KEY_HALF = new bw_UserKeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "clientKeyHalf", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});
/**
 * Indicates the user has been warned about the security implications of using biometrics and, depending on the OS,
 * recommended to require a password on first unlock of an application instance.
 */
const bw_DISMISSED_REQUIRE_PASSWORD_ON_START_CALLOUT = new bw_UserKeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "dismissedBiometricRequirePasswordOnStartCallout", {
    deserializer: (obj) => obj,
    clearOn: [],
});
/**
 * Stores whether the user has elected to cancel the biometric prompt. This is stored on disk due to process-reload
 * wiping memory state. We don't want to prompt the user again if they've elected to cancel.
 */
const bw_PROMPT_CANCELLED = bw_KeyDefinition.record(bw_BIOMETRIC_SETTINGS_DISK, "promptCancelled", {
    deserializer: (obj) => obj,
});
/**
 * Stores whether the user has elected to automatically prompt for biometric unlock on application start.
 */
const bw_PROMPT_AUTOMATICALLY = new bw_UserKeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "promptAutomatically", {
    deserializer: (obj) => obj,
    clearOn: [],
});
/**
 * Stores whether or not IPC handshake has been validated this session.
 */
const bw_FINGERPRINT_VALIDATED = new bw_KeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "fingerprintValidated", {
    deserializer: (obj) => obj,
});
/**
 * Last process reload time
 */
const bw_LAST_PROCESS_RELOAD = new bw_KeyDefinition(bw_BIOMETRIC_SETTINGS_DISK, "lastProcessReload", {
    deserializer: (obj) => new Date(obj),
});

;// ../../libs/key-management/src/biometrics/biometric-state.service.ts
var bw_biometric_state_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_BiometricStateService {
}
class bw_DefaultBiometricStateService {
    constructor(stateProvider) {
        this.stateProvider = stateProvider;
        this.biometricUnlockEnabledState = this.stateProvider.getActive(bw_BIOMETRIC_UNLOCK_ENABLED);
        this.biometricUnlockEnabled$ = this.biometricUnlockEnabledState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)(Boolean));
        this.requirePasswordOnStartState = this.stateProvider.getActive(bw_REQUIRE_PASSWORD_ON_START);
        this.requirePasswordOnStart$ = this.requirePasswordOnStartState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((value) => !!value));
        this.encryptedClientKeyHalfState = this.stateProvider.getActive(bw_ENCRYPTED_CLIENT_KEY_HALF);
        this.encryptedClientKeyHalf$ = this.encryptedClientKeyHalfState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)(bw_encryptedClientKeyHalfToEncString));
        this.dismissedRequirePasswordOnStartCalloutState = this.stateProvider.getActive(bw_DISMISSED_REQUIRE_PASSWORD_ON_START_CALLOUT);
        this.dismissedRequirePasswordOnStartCallout$ =
            this.dismissedRequirePasswordOnStartCalloutState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)(Boolean));
        this.promptCancelledState = this.stateProvider.getGlobal(bw_PROMPT_CANCELLED);
        this.promptCancelled$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.stateProvider.activeUserId$,
            this.promptCancelledState.state$,
        ]).pipe((0,bw_external_rxjs_namespaceObject.map)(([userId, record]) => {
            var _a;
            return userId != null ? ((_a = record === null || record === void 0 ? void 0 : record[userId]) !== null && _a !== void 0 ? _a : false) : false;
        }));
        this.promptAutomaticallyState = this.stateProvider.getActive(bw_PROMPT_AUTOMATICALLY);
        this.promptAutomatically$ = this.promptAutomaticallyState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)(Boolean));
        this.fingerprintValidatedState = this.stateProvider.getGlobal(bw_FINGERPRINT_VALIDATED);
        this.fingerprintValidated$ = this.fingerprintValidatedState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)(Boolean));
        this.lastProcessReloadState = this.stateProvider.getGlobal(bw_LAST_PROCESS_RELOAD);
        this.lastProcessReload$ = this.lastProcessReloadState.state$;
    }
    setBiometricUnlockEnabled(enabled) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.biometricUnlockEnabledState.update(() => enabled);
        });
    }
    getBiometricUnlockEnabled(userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_BIOMETRIC_UNLOCK_ENABLED).state$.pipe((0,bw_external_rxjs_namespaceObject.map)(Boolean)));
        });
    }
    setRequirePasswordOnStart(value) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            let currentActiveId = undefined;
            yield this.requirePasswordOnStartState.update((_, [userId]) => {
                currentActiveId = userId;
                return value;
            }, {
                combineLatestWith: this.requirePasswordOnStartState.combinedState$,
            });
            if (!value && currentActiveId) {
                yield this.removeEncryptedClientKeyHalf(currentActiveId);
            }
        });
    }
    setEncryptedClientKeyHalf(encryptedKeyHalf, userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const value = (_a = encryptedKeyHalf === null || encryptedKeyHalf === void 0 ? void 0 : encryptedKeyHalf.encryptedString) !== null && _a !== void 0 ? _a : null;
            if (userId) {
                yield this.stateProvider.getUser(userId, bw_ENCRYPTED_CLIENT_KEY_HALF).update(() => value);
            }
            else {
                yield this.encryptedClientKeyHalfState.update(() => value);
            }
        });
    }
    removeEncryptedClientKeyHalf(userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_ENCRYPTED_CLIENT_KEY_HALF).update(() => null);
        });
    }
    getRequirePasswordOnStart(userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            return !!(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_REQUIRE_PASSWORD_ON_START).state$));
        });
    }
    getEncryptedClientKeyHalf(userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider
                .getUser(userId, bw_ENCRYPTED_CLIENT_KEY_HALF)
                .state$.pipe((0,bw_external_rxjs_namespaceObject.map)(bw_encryptedClientKeyHalfToEncString)));
        });
    }
    logout(userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_ENCRYPTED_CLIENT_KEY_HALF).update(() => null);
            yield this.resetUserPromptCancelled(userId);
            // Persist auto prompt setting through logout
            // Persist dismissed require password on start callout through logout
        });
    }
    setDismissedRequirePasswordOnStartCallout() {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.dismissedRequirePasswordOnStartCalloutState.update(() => true);
        });
    }
    resetUserPromptCancelled(userId) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getGlobal(bw_PROMPT_CANCELLED).update((data, activeUserId) => {
                if (data != null) {
                    delete data[userId !== null && userId !== void 0 ? userId : activeUserId];
                }
                return data;
            }, {
                combineLatestWith: this.stateProvider.activeUserId$,
                shouldUpdate: (data, activeUserId) => (data === null || data === void 0 ? void 0 : data[userId !== null && userId !== void 0 ? userId : activeUserId]) != null,
            });
        });
    }
    setUserPromptCancelled() {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.promptCancelledState.update((record, userId) => {
                if (userId != null) {
                    record !== null && record !== void 0 ? record : (record = {});
                    record[userId] = true;
                }
                return record;
            }, {
                combineLatestWith: this.stateProvider.activeUserId$,
                shouldUpdate: (_, userId) => {
                    if (userId == null) {
                        throw new Error("Cannot update biometric prompt cancelled state without an active user");
                    }
                    return true;
                },
            });
        });
    }
    resetAllPromptCancelled() {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.promptCancelledState.update(() => null);
        });
    }
    setPromptAutomatically(prompt) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.promptAutomaticallyState.update(() => prompt);
        });
    }
    setFingerprintValidated(validated) {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.fingerprintValidatedState.update(() => validated);
        });
    }
    updateLastProcessReload() {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.lastProcessReloadState.update(() => new Date());
        });
    }
    getLastProcessReload() {
        return bw_biometric_state_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.lastProcessReload$);
        });
    }
}
function bw_encryptedClientKeyHalfToEncString(encryptedKeyHalf) {
    return encryptedKeyHalf == null ? null : new bw_enc_string_EncString(encryptedKeyHalf);
}

;// ../../libs/key-management/src/biometrics/biometrics-status.ts
var bw_BiometricsStatus;
(function (BiometricsStatus) {
    /** For the biometrics interface, this means that biometric unlock is available and can be used. Querying for the user specifically, this means that biometric can be used for to unlock this user */
    BiometricsStatus[BiometricsStatus["Available"] = 0] = "Available";
    /** Biometrics cannot be used, because the userkey needs to first be unlocked by the user's password, because unlock needs some volatile data that is not available on app-start */
    BiometricsStatus[BiometricsStatus["UnlockNeeded"] = 1] = "UnlockNeeded";
    /** Biometric hardware is not available (i.e laptop folded shut, sensor unplugged) */
    BiometricsStatus[BiometricsStatus["HardwareUnavailable"] = 2] = "HardwareUnavailable";
    /** Only relevant for linux, this means that polkit policies need to be set up and that can happen automatically */
    BiometricsStatus[BiometricsStatus["AutoSetupNeeded"] = 3] = "AutoSetupNeeded";
    /** Only relevant for linux, this means that polkit policies need to be set up but that needs to be done manually */
    BiometricsStatus[BiometricsStatus["ManualSetupNeeded"] = 4] = "ManualSetupNeeded";
    /** Biometrics is not implemented for this platform (i.e web) */
    BiometricsStatus[BiometricsStatus["PlatformUnsupported"] = 5] = "PlatformUnsupported";
    /** Browser extension cannot connect to the desktop app to use biometrics */
    BiometricsStatus[BiometricsStatus["DesktopDisconnected"] = 6] = "DesktopDisconnected";
    /** Biometrics is not enabled in the desktop app/extension (current app) */
    BiometricsStatus[BiometricsStatus["NotEnabledLocally"] = 7] = "NotEnabledLocally";
    /** Only on browser extension; Biometrics is not enabled in the desktop app */
    BiometricsStatus[BiometricsStatus["NotEnabledInConnectedDesktopApp"] = 8] = "NotEnabledInConnectedDesktopApp";
    /** Browser extension does not have the permission to talk to the desktop app */
    BiometricsStatus[BiometricsStatus["NativeMessagingPermissionMissing"] = 9] = "NativeMessagingPermissionMissing";
})(bw_BiometricsStatus || (bw_BiometricsStatus = {}));

;// ../../libs/key-management/src/biometrics/biometrics-commands.ts
var bw_BiometricsCommands;
(function (BiometricsCommands) {
    /** Perform biometric authentication for the system's user. Does not require setup, and does not return cryptographic material, only yes or no. */
    BiometricsCommands["AuthenticateWithBiometrics"] = "authenticateWithBiometrics";
    /** Get biometric status of the system, and can be used before biometrics is set up. Only returns data about the biometrics system, not about availability of cryptographic material */
    BiometricsCommands["GetBiometricsStatus"] = "getBiometricsStatus";
    /** Perform biometric authentication for the system's user for the given bitwarden account's credentials. This returns cryptographic material that can be used to unlock the vault. */
    BiometricsCommands["UnlockWithBiometricsForUser"] = "unlockWithBiometricsForUser";
    /** Get biometric status for a specific user account. This includes both information about availability of cryptographic material (is the user configured for biometric unlock? is a masterpassword unlock needed? But also information about the biometric system's availability in a single status) */
    BiometricsCommands["GetBiometricsStatusForUser"] = "getBiometricsStatusForUser";
    // legacy
    BiometricsCommands["Unlock"] = "biometricUnlock";
    BiometricsCommands["IsAvailable"] = "biometricUnlockAvailable";
})(bw_BiometricsCommands || (bw_BiometricsCommands = {}));

;// ../../libs/key-management/src/biometrics/biometric.service.ts
/**
 * The biometrics service is used to provide access to the status of and access to biometric functionality on the platforms.
 */
class bw_BiometricsService {
    supportsBiometric() {
        throw new Error("Method not implemented.");
    }
}

;// ../../libs/key-management/src/abstractions/key.service.ts
class bw_UserPrivateKeyDecryptionFailedError extends Error {
    constructor() {
        super("Failed to decrypt the user's private key.");
    }
}
class bw_KeyService {
}

;// external "big-integer"
const bw_external_big_integer_namespaceObject = require("big-integer");
;// ../../libs/common/src/admin-console/models/domain/encrypted-organization-key.ts
var bw_encrypted_organization_key_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_BaseEncryptedOrganizationKey {
    static fromData(data) {
        switch (data.type) {
            case "organization":
                return new bw_EncryptedOrganizationKey(data.key);
            case "provider":
                return new bw_ProviderEncryptedOrganizationKey(data.key, data.providerId);
            default:
                return null;
        }
    }
    static isProviderEncrypted(key) {
        return key.toData().type === "provider";
    }
}
class bw_EncryptedOrganizationKey {
    constructor(key) {
        this.key = key;
    }
    decrypt(encryptService, privateKey) {
        return bw_encrypted_organization_key_awaiter(this, void 0, void 0, function* () {
            const decValue = yield encryptService.rsaDecrypt(this.encryptedOrganizationKey, privateKey);
            return new bw_SymmetricCryptoKey(decValue);
        });
    }
    get encryptedOrganizationKey() {
        return new bw_enc_string_EncString(this.key);
    }
    toData() {
        return {
            type: "organization",
            key: this.key,
        };
    }
}
class bw_ProviderEncryptedOrganizationKey {
    constructor(key, providerId) {
        this.key = key;
        this.providerId = providerId;
    }
    decrypt(encryptService, providerKeys) {
        return bw_encrypted_organization_key_awaiter(this, void 0, void 0, function* () {
            const decValue = yield encryptService.decryptToBytes(new bw_enc_string_EncString(this.key), providerKeys[this.providerId]);
            if (decValue == null) {
                throw new Error("Failed to decrypt organization key");
            }
            return new bw_SymmetricCryptoKey(decValue);
        });
    }
    get encryptedOrganizationKey() {
        return new bw_enc_string_EncString(this.key);
    }
    toData() {
        return {
            type: "provider",
            key: this.key,
            providerId: this.providerId,
        };
    }
}

;// ../../libs/common/src/admin-console/enums/organization-api-key-type.enum.ts
var bw_OrganizationApiKeyType;
(function (OrganizationApiKeyType) {
    OrganizationApiKeyType[OrganizationApiKeyType["Default"] = 0] = "Default";
    OrganizationApiKeyType[OrganizationApiKeyType["BillingSync"] = 1] = "BillingSync";
    OrganizationApiKeyType[OrganizationApiKeyType["Scim"] = 2] = "Scim";
})(bw_OrganizationApiKeyType || (bw_OrganizationApiKeyType = {}));

;// ../../libs/common/src/admin-console/enums/organization-connection-type.enum.ts
var bw_OrganizationConnectionType;
(function (OrganizationConnectionType) {
    OrganizationConnectionType[OrganizationConnectionType["CloudBillingSync"] = 1] = "CloudBillingSync";
    OrganizationConnectionType[OrganizationConnectionType["Scim"] = 2] = "Scim";
})(bw_OrganizationConnectionType || (bw_OrganizationConnectionType = {}));

;// ../../libs/common/src/admin-console/enums/organization-user-status-type.enum.ts
var bw_OrganizationUserStatusType;
(function (OrganizationUserStatusType) {
    OrganizationUserStatusType[OrganizationUserStatusType["Invited"] = 0] = "Invited";
    OrganizationUserStatusType[OrganizationUserStatusType["Accepted"] = 1] = "Accepted";
    OrganizationUserStatusType[OrganizationUserStatusType["Confirmed"] = 2] = "Confirmed";
    OrganizationUserStatusType[OrganizationUserStatusType["Revoked"] = -1] = "Revoked";
})(bw_OrganizationUserStatusType || (bw_OrganizationUserStatusType = {}));

;// ../../libs/common/src/admin-console/enums/organization-user-type.enum.ts
var bw_OrganizationUserType;
(function (OrganizationUserType) {
    OrganizationUserType[OrganizationUserType["Owner"] = 0] = "Owner";
    OrganizationUserType[OrganizationUserType["Admin"] = 1] = "Admin";
    OrganizationUserType[OrganizationUserType["User"] = 2] = "User";
    // Manager = 3 has been intentionally permanently deleted
    OrganizationUserType[OrganizationUserType["Custom"] = 4] = "Custom";
})(bw_OrganizationUserType || (bw_OrganizationUserType = {}));

;// ../../libs/common/src/admin-console/enums/policy-type.enum.ts
var bw_policy_type_enum_PolicyType;
(function (PolicyType) {
    PolicyType[PolicyType["TwoFactorAuthentication"] = 0] = "TwoFactorAuthentication";
    PolicyType[PolicyType["MasterPassword"] = 1] = "MasterPassword";
    PolicyType[PolicyType["PasswordGenerator"] = 2] = "PasswordGenerator";
    PolicyType[PolicyType["SingleOrg"] = 3] = "SingleOrg";
    PolicyType[PolicyType["RequireSso"] = 4] = "RequireSso";
    PolicyType[PolicyType["PersonalOwnership"] = 5] = "PersonalOwnership";
    PolicyType[PolicyType["DisableSend"] = 6] = "DisableSend";
    PolicyType[PolicyType["SendOptions"] = 7] = "SendOptions";
    PolicyType[PolicyType["ResetPassword"] = 8] = "ResetPassword";
    PolicyType[PolicyType["MaximumVaultTimeout"] = 9] = "MaximumVaultTimeout";
    PolicyType[PolicyType["DisablePersonalVaultExport"] = 10] = "DisablePersonalVaultExport";
    PolicyType[PolicyType["ActivateAutofill"] = 11] = "ActivateAutofill";
    PolicyType[PolicyType["AutomaticAppLogIn"] = 12] = "AutomaticAppLogIn";
    PolicyType[PolicyType["FreeFamiliesSponsorshipPolicy"] = 13] = "FreeFamiliesSponsorshipPolicy";
    PolicyType[PolicyType["RemoveUnlockWithPin"] = 14] = "RemoveUnlockWithPin";
})(bw_policy_type_enum_PolicyType || (bw_policy_type_enum_PolicyType = {}));

;// ../../libs/common/src/admin-console/enums/provider-type.enum.ts
var bw_ProviderType;
(function (ProviderType) {
    ProviderType[ProviderType["Msp"] = 0] = "Msp";
    ProviderType[ProviderType["Reseller"] = 1] = "Reseller";
    ProviderType[ProviderType["MultiOrganizationEnterprise"] = 2] = "MultiOrganizationEnterprise";
})(bw_ProviderType || (bw_ProviderType = {}));

;// ../../libs/common/src/admin-console/enums/provider-user-status-type.enum.ts
var bw_ProviderUserStatusType;
(function (ProviderUserStatusType) {
    ProviderUserStatusType[ProviderUserStatusType["Invited"] = 0] = "Invited";
    ProviderUserStatusType[ProviderUserStatusType["Accepted"] = 1] = "Accepted";
    ProviderUserStatusType[ProviderUserStatusType["Confirmed"] = 2] = "Confirmed";
    ProviderUserStatusType[ProviderUserStatusType["Revoked"] = -1] = "Revoked";
})(bw_ProviderUserStatusType || (bw_ProviderUserStatusType = {}));

;// ../../libs/common/src/admin-console/enums/provider-user-type.enum.ts
var bw_ProviderUserType;
(function (ProviderUserType) {
    ProviderUserType[ProviderUserType["ProviderAdmin"] = 0] = "ProviderAdmin";
    ProviderUserType[ProviderUserType["ServiceUser"] = 1] = "ServiceUser";
})(bw_ProviderUserType || (bw_ProviderUserType = {}));

;// ../../libs/common/src/admin-console/enums/scim-provider-type.enum.ts
var bw_ScimProviderType;
(function (ScimProviderType) {
    ScimProviderType[ScimProviderType["Default"] = 0] = "Default";
    ScimProviderType[ScimProviderType["AzureAd"] = 1] = "AzureAd";
    ScimProviderType[ScimProviderType["Okta"] = 2] = "Okta";
    ScimProviderType[ScimProviderType["OneLogin"] = 3] = "OneLogin";
    ScimProviderType[ScimProviderType["JumpCloud"] = 4] = "JumpCloud";
    ScimProviderType[ScimProviderType["GoogleWorkspace"] = 5] = "GoogleWorkspace";
    ScimProviderType[ScimProviderType["Rippling"] = 6] = "Rippling";
})(bw_ScimProviderType || (bw_ScimProviderType = {}));

;// ../../libs/common/src/admin-console/enums/provider-status-type.enum.ts
var bw_ProviderStatusType;
(function (ProviderStatusType) {
    ProviderStatusType[ProviderStatusType["Pending"] = 0] = "Pending";
    ProviderStatusType[ProviderStatusType["Created"] = 1] = "Created";
    ProviderStatusType[ProviderStatusType["Billable"] = 2] = "Billable";
})(bw_ProviderStatusType || (bw_ProviderStatusType = {}));

;// ../../libs/common/src/admin-console/enums/index.ts











;// ../../libs/common/src/key-management/vault-timeout/enums/vault-timeout-action.enum.ts
var bw_VaultTimeoutAction;
(function (VaultTimeoutAction) {
    VaultTimeoutAction["Lock"] = "lock";
    VaultTimeoutAction["LogOut"] = "logOut";
})(bw_VaultTimeoutAction || (bw_VaultTimeoutAction = {}));

;// ../../libs/common/src/key-management/vault-timeout/types/vault-timeout.type.ts
// Note: the below comments are just for documenting what they used to be.
const bw_VaultTimeoutStringType = {
    Never: "never", // null
    OnRestart: "onRestart", // -1
    OnLocked: "onLocked", // -2
    OnSleep: "onSleep", // -3
    OnIdle: "onIdle", // -4
};

;// ../../libs/common/src/key-management/vault-timeout/services/vault-timeout-settings.state.ts

/**
 * Settings use disk storage and local storage on web so settings can persist after logout
 * in order for us to know if the user's chose to never lock their vault or not.
 * When the user has never lock selected, we have to set the user key in memory
 * from the user auto unlock key stored on disk on client bootstrap.
 */
const bw_VAULT_TIMEOUT_ACTION = new bw_UserKeyDefinition(bw_VAULT_TIMEOUT_SETTINGS_DISK_LOCAL, "vaultTimeoutAction", {
    deserializer: (vaultTimeoutAction) => vaultTimeoutAction,
    clearOn: [], // persisted on logout
});
const bw_VAULT_TIMEOUT = new bw_UserKeyDefinition(bw_VAULT_TIMEOUT_SETTINGS_DISK_LOCAL, "vaultTimeout", {
    deserializer: (vaultTimeout) => vaultTimeout,
    clearOn: [], // persisted on logout
});

;// ../../libs/common/src/key-management/vault-timeout/services/vault-timeout-settings.service.ts
var bw_vault_timeout_settings_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_VaultTimeoutSettingsService {
    constructor(accountService, pinService, userDecryptionOptionsService, keyService, tokenService, policyService, biometricStateService, stateProvider, logService, defaultVaultTimeout) {
        this.accountService = accountService;
        this.pinService = pinService;
        this.userDecryptionOptionsService = userDecryptionOptionsService;
        this.keyService = keyService;
        this.tokenService = tokenService;
        this.policyService = policyService;
        this.biometricStateService = biometricStateService;
        this.stateProvider = stateProvider;
        this.logService = logService;
        this.defaultVaultTimeout = defaultVaultTimeout;
    }
    setVaultTimeoutOptions(userId, timeout, action) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("User id required. Cannot set vault timeout settings.");
            }
            if (timeout == null) {
                throw new Error("Vault Timeout cannot be null.");
            }
            if (action == null) {
                throw new Error("Vault Timeout Action cannot be null.");
            }
            // We swap these tokens from being on disk for lock actions, and in memory for logout actions
            // Get them here to set them to their new location after changing the timeout action and clearing if needed
            const accessToken = yield this.tokenService.getAccessToken();
            const refreshToken = yield this.tokenService.getRefreshToken();
            const clientId = yield this.tokenService.getClientId();
            const clientSecret = yield this.tokenService.getClientSecret();
            yield this.setVaultTimeout(userId, timeout);
            if (timeout != bw_VaultTimeoutStringType.Never && action === bw_VaultTimeoutAction.LogOut) {
                // if we have a vault timeout and the action is log out, reset tokens
                // as the tokens were stored on disk and now should be stored in memory
                yield this.tokenService.clearTokens();
            }
            yield this.setVaultTimeoutAction(userId, action);
            yield this.tokenService.setTokens(accessToken, action, timeout, refreshToken, [
                clientId,
                clientSecret,
            ]);
            yield this.keyService.refreshAdditionalKeys();
        });
    }
    availableVaultTimeoutActions$(userId) {
        return (0,bw_external_rxjs_namespaceObject.defer)(() => this.getAvailableVaultTimeoutActions(userId));
    }
    canLock(userId) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            const availableVaultTimeoutActions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.availableVaultTimeoutActions$(userId));
            return (availableVaultTimeoutActions === null || availableVaultTimeoutActions === void 0 ? void 0 : availableVaultTimeoutActions.includes(bw_VaultTimeoutAction.Lock)) || false;
        });
    }
    isBiometricLockSet(userId) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            const biometricUnlockPromise = userId == null
                ? (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.biometricStateService.biometricUnlockEnabled$)
                : this.biometricStateService.getBiometricUnlockEnabled(userId);
            return yield biometricUnlockPromise;
        });
    }
    setVaultTimeout(userId, timeout) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("User id required. Cannot set vault timeout.");
            }
            if (timeout == null) {
                throw new Error("Vault Timeout cannot be null.");
            }
            yield this.stateProvider.setUserState(bw_VAULT_TIMEOUT, timeout, userId);
        });
    }
    getVaultTimeoutByUserId$(userId) {
        if (!userId) {
            throw new Error("User id required. Cannot get vault timeout.");
        }
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.stateProvider.getUserState$(bw_VAULT_TIMEOUT, userId),
            this.getMaxVaultTimeoutPolicyByUserId$(userId),
        ]).pipe((0,bw_external_rxjs_namespaceObject.switchMap)(([currentVaultTimeout, maxVaultTimeoutPolicy]) => {
            return (0,bw_external_rxjs_namespaceObject.from)(this.determineVaultTimeout(currentVaultTimeout, maxVaultTimeoutPolicy)).pipe((0,bw_external_rxjs_namespaceObject.tap)((vaultTimeout) => {
                // As a side effect, set the new value determined by determineVaultTimeout into state if it's different from the current
                if (vaultTimeout !== currentVaultTimeout) {
                    return this.stateProvider.setUserState(bw_VAULT_TIMEOUT, vaultTimeout, userId);
                }
            }), (0,bw_external_rxjs_namespaceObject.catchError)((error) => {
                // Protect outer observable from canceling on error by catching and returning EMPTY
                this.logService.error(`Error getting vault timeout: ${error}`);
                return bw_external_rxjs_namespaceObject.EMPTY;
            }));
        }), (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(), // Avoid having the set side effect trigger a new emission of the same action
        (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
    }
    determineVaultTimeout(currentVaultTimeout, maxVaultTimeoutPolicy) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            // if current vault timeout is null, apply the client specific default
            currentVaultTimeout = currentVaultTimeout !== null && currentVaultTimeout !== void 0 ? currentVaultTimeout : this.defaultVaultTimeout;
            // If no policy applies, return the current vault timeout
            if (!maxVaultTimeoutPolicy) {
                return currentVaultTimeout;
            }
            // User is subject to a max vault timeout policy
            const maxVaultTimeoutPolicyData = maxVaultTimeoutPolicy.data;
            // If the current vault timeout is not numeric, change it to the policy compliant value
            if (typeof currentVaultTimeout === "string") {
                return maxVaultTimeoutPolicyData.minutes;
            }
            // For numeric vault timeouts, ensure they are smaller than maximum allowed value according to policy
            const policyCompliantTimeout = Math.min(currentVaultTimeout, maxVaultTimeoutPolicyData.minutes);
            return policyCompliantTimeout;
        });
    }
    setVaultTimeoutAction(userId, action) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("User id required. Cannot set vault timeout action.");
            }
            if (!action) {
                throw new Error("Vault Timeout Action cannot be null");
            }
            yield this.stateProvider.setUserState(bw_VAULT_TIMEOUT_ACTION, action, userId);
        });
    }
    getVaultTimeoutActionByUserId$(userId) {
        if (!userId) {
            throw new Error("User id required. Cannot get vault timeout action.");
        }
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.stateProvider.getUserState$(bw_VAULT_TIMEOUT_ACTION, userId),
            this.getMaxVaultTimeoutPolicyByUserId$(userId),
        ]).pipe((0,bw_external_rxjs_namespaceObject.switchMap)(([currentVaultTimeoutAction, maxVaultTimeoutPolicy]) => {
            return (0,bw_external_rxjs_namespaceObject.from)(this.determineVaultTimeoutAction(userId, currentVaultTimeoutAction, maxVaultTimeoutPolicy)).pipe((0,bw_external_rxjs_namespaceObject.tap)((vaultTimeoutAction) => {
                // As a side effect, set the new value determined by determineVaultTimeout into state if it's different from the current
                // We want to avoid having a null timeout action always so we set it to the default if it is null
                // and if the user becomes subject to a policy that requires a specific action, we set it to that
                if (vaultTimeoutAction !== currentVaultTimeoutAction) {
                    return this.stateProvider.setUserState(bw_VAULT_TIMEOUT_ACTION, vaultTimeoutAction, userId);
                }
            }), (0,bw_external_rxjs_namespaceObject.catchError)((error) => {
                // Protect outer observable from canceling on error by catching and returning EMPTY
                this.logService.error(`Error getting vault timeout: ${error}`);
                return bw_external_rxjs_namespaceObject.EMPTY;
            }));
        }), (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(), // Avoid having the set side effect trigger a new emission of the same action
        (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
    }
    determineVaultTimeoutAction(userId, currentVaultTimeoutAction, maxVaultTimeoutPolicy) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const availableVaultTimeoutActions = yield this.getAvailableVaultTimeoutActions(userId);
            if (availableVaultTimeoutActions.length === 1) {
                return availableVaultTimeoutActions[0];
            }
            if (((_a = maxVaultTimeoutPolicy === null || maxVaultTimeoutPolicy === void 0 ? void 0 : maxVaultTimeoutPolicy.data) === null || _a === void 0 ? void 0 : _a.action) &&
                availableVaultTimeoutActions.includes(maxVaultTimeoutPolicy.data.action)) {
                // return policy defined vault timeout action
                return maxVaultTimeoutPolicy.data.action;
            }
            // No policy applies from here on
            // If the current vault timeout is null and lock is an option, set it as the default
            if (currentVaultTimeoutAction == null &&
                availableVaultTimeoutActions.includes(bw_VaultTimeoutAction.Lock)) {
                return bw_VaultTimeoutAction.Lock;
            }
            return currentVaultTimeoutAction;
        });
    }
    getMaxVaultTimeoutPolicyByUserId$(userId) {
        if (!userId) {
            throw new Error("User id required. Cannot get max vault timeout policy.");
        }
        return this.policyService
            .getAll$(bw_policy_type_enum_PolicyType.MaximumVaultTimeout, userId)
            .pipe((0,bw_external_rxjs_namespaceObject.map)((policies) => { var _a; return (_a = policies[0]) !== null && _a !== void 0 ? _a : null; }));
    }
    getAvailableVaultTimeoutActions(userId) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            userId !== null && userId !== void 0 ? userId : (userId = (_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$))) === null || _a === void 0 ? void 0 : _a.id);
            const availableActions = [bw_VaultTimeoutAction.LogOut];
            const canLock = (yield this.userHasMasterPassword(userId)) ||
                (yield this.pinService.isPinSet(userId)) ||
                (yield this.isBiometricLockSet(userId));
            if (canLock) {
                availableActions.push(bw_VaultTimeoutAction.Lock);
            }
            return availableActions;
        });
    }
    clear(userId) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.keyService.clearPinKeys(userId);
        });
    }
    userHasMasterPassword(userId) {
        return bw_vault_timeout_settings_service_awaiter(this, void 0, void 0, function* () {
            if (userId) {
                const decryptionOptions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userDecryptionOptionsService.userDecryptionOptionsById$(userId));
                return !!(decryptionOptions === null || decryptionOptions === void 0 ? void 0 : decryptionOptions.hasMasterPassword);
            }
            else {
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userDecryptionOptionsService.hasMasterPassword$);
            }
        });
    }
}

;// ../../libs/common/src/key-management/vault-timeout/services/vault-timeout.service.ts
var bw_vault_timeout_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_VaultTimeoutService {
    constructor(accountService, masterPasswordService, cipherService, folderService, collectionService, platformUtilsService, messagingService, searchService, stateService, authService, vaultTimeoutSettingsService, stateEventRunnerService, taskSchedulerService, logService, biometricService, lockedCallback = null, loggedOutCallback = null) {
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.collectionService = collectionService;
        this.platformUtilsService = platformUtilsService;
        this.messagingService = messagingService;
        this.searchService = searchService;
        this.stateService = stateService;
        this.authService = authService;
        this.vaultTimeoutSettingsService = vaultTimeoutSettingsService;
        this.stateEventRunnerService = stateEventRunnerService;
        this.taskSchedulerService = taskSchedulerService;
        this.logService = logService;
        this.biometricService = biometricService;
        this.lockedCallback = lockedCallback;
        this.loggedOutCallback = loggedOutCallback;
        this.inited = false;
        this.taskSchedulerService.registerTaskHandler(bw_ScheduledTaskNames.vaultTimeoutCheckInterval, () => this.checkVaultTimeout());
    }
    init(checkOnInterval) {
        return bw_vault_timeout_service_awaiter(this, void 0, void 0, function* () {
            if (this.inited) {
                return;
            }
            this.inited = true;
            if (checkOnInterval) {
                this.startCheck();
            }
        });
    }
    startCheck() {
        this.checkVaultTimeout().catch((error) => this.logService.error(error));
        this.taskSchedulerService.setInterval(bw_ScheduledTaskNames.vaultTimeoutCheckInterval, 10 * 1000);
    }
    checkVaultTimeout() {
        return bw_vault_timeout_service_awaiter(this, void 0, void 0, function* () {
            // Get whether or not the view is open a single time so it can be compared for each user
            const isViewOpen = yield this.platformUtilsService.isViewOpen();
            yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)((0,bw_external_rxjs_namespaceObject.combineLatest)([
                this.accountService.activeAccount$,
                this.accountService.accountActivity$,
            ]).pipe((0,bw_external_rxjs_namespaceObject.concatMap)((_a) => bw_vault_timeout_service_awaiter(this, [_a], void 0, function* ([activeAccount, accountActivity]) {
                const activeUserId = activeAccount === null || activeAccount === void 0 ? void 0 : activeAccount.id;
                for (const userIdString in accountActivity) {
                    const userId = userIdString;
                    if (userId != null &&
                        (yield this.shouldLock(userId, accountActivity[userId], activeUserId, isViewOpen))) {
                        yield this.executeTimeoutAction(userId);
                    }
                }
            }))));
        });
    }
    lock(userId) {
        return bw_vault_timeout_service_awaiter(this, void 0, void 0, function* () {
            yield this.biometricService.setShouldAutopromptNow(false);
            const authed = yield this.stateService.getIsAuthenticated({ userId: userId });
            if (!authed) {
                return;
            }
            const availableActions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.availableVaultTimeoutActions$(userId));
            const supportsLock = availableActions.includes(bw_VaultTimeoutAction.Lock);
            if (!supportsLock) {
                yield this.logOut(userId);
            }
            const currentUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
            const lockingUserId = userId !== null && userId !== void 0 ? userId : currentUserId;
            // HACK: Start listening for the transition of the locking user from something to the locked state.
            // This is very much a hack to ensure that the authentication status to retrievable right after
            // it does its work. Particularly the `lockedCallback` and `"locked"` message. Instead
            // lockedCallback should be deprecated and people should subscribe and react to `authStatusFor$` themselves.
            const lockPromise = (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService.authStatusFor$(lockingUserId).pipe((0,bw_external_rxjs_namespaceObject.filter)((authStatus) => authStatus === bw_authentication_status_AuthenticationStatus.Locked), (0,bw_external_rxjs_namespaceObject.timeout)({
                first: 5000,
                with: () => {
                    throw new Error("The lock process did not complete in a reasonable amount of time.");
                },
            })));
            if (userId == null || userId === currentUserId) {
                yield this.collectionService.clearActiveUserCache();
            }
            yield this.searchService.clearIndex(lockingUserId);
            yield this.folderService.clearDecryptedFolderState(lockingUserId);
            yield this.masterPasswordService.clearMasterKey(lockingUserId);
            yield this.stateService.setUserKeyAutoUnlock(null, { userId: lockingUserId });
            yield this.stateService.setCryptoMasterKeyAuto(null, { userId: lockingUserId });
            yield this.cipherService.clearCache(lockingUserId);
            yield this.stateEventRunnerService.handleEvent("lock", lockingUserId);
            // HACK: Sit here and wait for the the auth status to transition to `Locked`
            // to ensure the message and lockedCallback will get the correct status
            // if/when they call it.
            yield lockPromise;
            this.messagingService.send("locked", { userId: lockingUserId });
            if (this.lockedCallback != null) {
                yield this.lockedCallback(userId);
            }
        });
    }
    logOut(userId) {
        return bw_vault_timeout_service_awaiter(this, void 0, void 0, function* () {
            if (this.loggedOutCallback != null) {
                yield this.loggedOutCallback("vaultTimeout", userId);
            }
        });
    }
    shouldLock(userId, lastActive, activeUserId, isViewOpen) {
        return bw_vault_timeout_service_awaiter(this, void 0, void 0, function* () {
            if (isViewOpen && userId === activeUserId) {
                // We know a view is open and this is the currently active user
                // which means they are likely looking at their vault
                // and they should not lock.
                return false;
            }
            const authStatus = yield this.authService.getAuthStatus(userId);
            if (authStatus === bw_authentication_status_AuthenticationStatus.Locked ||
                authStatus === bw_authentication_status_AuthenticationStatus.LoggedOut) {
                return false;
            }
            const vaultTimeout = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutByUserId$(userId));
            if (typeof vaultTimeout === "string") {
                return false;
            }
            if (lastActive == null) {
                return false;
            }
            const vaultTimeoutSeconds = vaultTimeout * 60;
            const diffSeconds = (new Date().getTime() - lastActive.getTime()) / 1000;
            return diffSeconds >= vaultTimeoutSeconds;
        });
    }
    executeTimeoutAction(userId) {
        return bw_vault_timeout_service_awaiter(this, void 0, void 0, function* () {
            const timeoutAction = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutActionByUserId$(userId));
            timeoutAction === bw_VaultTimeoutAction.LogOut
                ? yield this.logOut(userId)
                : yield this.lock(userId);
        });
    }
}

;// ../../libs/common/src/key-management/vault-timeout/index.ts







;// ../../libs/common/src/platform/misc/convert-values.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/**
 * Converts a record of keys and values into a record preserving the original key and converting each value into an {@link ObservableInput}.
 * @param project A function to project a given key and value pair into an {@link ObservableInput}
 */
function bw_convertValues(project) {
    return (0,bw_external_rxjs_namespaceObject.map)((inputRecord) => {
        if (inputRecord == null) {
            return null;
        }
        // Can't use TKey in here, have to use `PropertyKey`
        const result = {};
        for (const [key, value] of Object.entries(inputRecord)) {
            result[key] = project(key, value);
        }
        return result;
    });
}

;// ../../libs/common/src/platform/misc/wordlist.ts
// EFF's Long Wordlist from https://www.eff.org/dice
const bw_EFFLongWordList = [
    "abacus",
    "abdomen",
    "abdominal",
    "abide",
    "abiding",
    "ability",
    "ablaze",
    "able",
    "abnormal",
    "abrasion",
    "abrasive",
    "abreast",
    "abridge",
    "abroad",
    "abruptly",
    "absence",
    "absentee",
    "absently",
    "absinthe",
    "absolute",
    "absolve",
    "abstain",
    "abstract",
    "absurd",
    "accent",
    "acclaim",
    "acclimate",
    "accompany",
    "account",
    "accuracy",
    "accurate",
    "accustom",
    "acetone",
    "achiness",
    "aching",
    "acid",
    "acorn",
    "acquaint",
    "acquire",
    "acre",
    "acrobat",
    "acronym",
    "acting",
    "action",
    "activate",
    "activator",
    "active",
    "activism",
    "activist",
    "activity",
    "actress",
    "acts",
    "acutely",
    "acuteness",
    "aeration",
    "aerobics",
    "aerosol",
    "aerospace",
    "afar",
    "affair",
    "affected",
    "affecting",
    "affection",
    "affidavit",
    "affiliate",
    "affirm",
    "affix",
    "afflicted",
    "affluent",
    "afford",
    "affront",
    "aflame",
    "afloat",
    "aflutter",
    "afoot",
    "afraid",
    "afterglow",
    "afterlife",
    "aftermath",
    "aftermost",
    "afternoon",
    "aged",
    "ageless",
    "agency",
    "agenda",
    "agent",
    "aggregate",
    "aghast",
    "agile",
    "agility",
    "aging",
    "agnostic",
    "agonize",
    "agonizing",
    "agony",
    "agreeable",
    "agreeably",
    "agreed",
    "agreeing",
    "agreement",
    "aground",
    "ahead",
    "ahoy",
    "aide",
    "aids",
    "aim",
    "ajar",
    "alabaster",
    "alarm",
    "albatross",
    "album",
    "alfalfa",
    "algebra",
    "algorithm",
    "alias",
    "alibi",
    "alienable",
    "alienate",
    "aliens",
    "alike",
    "alive",
    "alkaline",
    "alkalize",
    "almanac",
    "almighty",
    "almost",
    "aloe",
    "aloft",
    "aloha",
    "alone",
    "alongside",
    "aloof",
    "alphabet",
    "alright",
    "although",
    "altitude",
    "alto",
    "aluminum",
    "alumni",
    "always",
    "amaretto",
    "amaze",
    "amazingly",
    "amber",
    "ambiance",
    "ambiguity",
    "ambiguous",
    "ambition",
    "ambitious",
    "ambulance",
    "ambush",
    "amendable",
    "amendment",
    "amends",
    "amenity",
    "amiable",
    "amicably",
    "amid",
    "amigo",
    "amino",
    "amiss",
    "ammonia",
    "ammonium",
    "amnesty",
    "amniotic",
    "among",
    "amount",
    "amperage",
    "ample",
    "amplifier",
    "amplify",
    "amply",
    "amuck",
    "amulet",
    "amusable",
    "amused",
    "amusement",
    "amuser",
    "amusing",
    "anaconda",
    "anaerobic",
    "anagram",
    "anatomist",
    "anatomy",
    "anchor",
    "anchovy",
    "ancient",
    "android",
    "anemia",
    "anemic",
    "aneurism",
    "anew",
    "angelfish",
    "angelic",
    "anger",
    "angled",
    "angler",
    "angles",
    "angling",
    "angrily",
    "angriness",
    "anguished",
    "angular",
    "animal",
    "animate",
    "animating",
    "animation",
    "animator",
    "anime",
    "animosity",
    "ankle",
    "annex",
    "annotate",
    "announcer",
    "annoying",
    "annually",
    "annuity",
    "anointer",
    "another",
    "answering",
    "antacid",
    "antarctic",
    "anteater",
    "antelope",
    "antennae",
    "anthem",
    "anthill",
    "anthology",
    "antibody",
    "antics",
    "antidote",
    "antihero",
    "antiquely",
    "antiques",
    "antiquity",
    "antirust",
    "antitoxic",
    "antitrust",
    "antiviral",
    "antivirus",
    "antler",
    "antonym",
    "antsy",
    "anvil",
    "anybody",
    "anyhow",
    "anymore",
    "anyone",
    "anyplace",
    "anything",
    "anytime",
    "anyway",
    "anywhere",
    "aorta",
    "apache",
    "apostle",
    "appealing",
    "appear",
    "appease",
    "appeasing",
    "appendage",
    "appendix",
    "appetite",
    "appetizer",
    "applaud",
    "applause",
    "apple",
    "appliance",
    "applicant",
    "applied",
    "apply",
    "appointee",
    "appraisal",
    "appraiser",
    "apprehend",
    "approach",
    "approval",
    "approve",
    "apricot",
    "april",
    "apron",
    "aptitude",
    "aptly",
    "aqua",
    "aqueduct",
    "arbitrary",
    "arbitrate",
    "ardently",
    "area",
    "arena",
    "arguable",
    "arguably",
    "argue",
    "arise",
    "armadillo",
    "armband",
    "armchair",
    "armed",
    "armful",
    "armhole",
    "arming",
    "armless",
    "armoire",
    "armored",
    "armory",
    "armrest",
    "army",
    "aroma",
    "arose",
    "around",
    "arousal",
    "arrange",
    "array",
    "arrest",
    "arrival",
    "arrive",
    "arrogance",
    "arrogant",
    "arson",
    "art",
    "ascend",
    "ascension",
    "ascent",
    "ascertain",
    "ashamed",
    "ashen",
    "ashes",
    "ashy",
    "aside",
    "askew",
    "asleep",
    "asparagus",
    "aspect",
    "aspirate",
    "aspire",
    "aspirin",
    "astonish",
    "astound",
    "astride",
    "astrology",
    "astronaut",
    "astronomy",
    "astute",
    "atlantic",
    "atlas",
    "atom",
    "atonable",
    "atop",
    "atrium",
    "atrocious",
    "atrophy",
    "attach",
    "attain",
    "attempt",
    "attendant",
    "attendee",
    "attention",
    "attentive",
    "attest",
    "attic",
    "attire",
    "attitude",
    "attractor",
    "attribute",
    "atypical",
    "auction",
    "audacious",
    "audacity",
    "audible",
    "audibly",
    "audience",
    "audio",
    "audition",
    "augmented",
    "august",
    "authentic",
    "author",
    "autism",
    "autistic",
    "autograph",
    "automaker",
    "automated",
    "automatic",
    "autopilot",
    "available",
    "avalanche",
    "avatar",
    "avenge",
    "avenging",
    "avenue",
    "average",
    "aversion",
    "avert",
    "aviation",
    "aviator",
    "avid",
    "avoid",
    "await",
    "awaken",
    "award",
    "aware",
    "awhile",
    "awkward",
    "awning",
    "awoke",
    "awry",
    "axis",
    "babble",
    "babbling",
    "babied",
    "baboon",
    "backache",
    "backboard",
    "backboned",
    "backdrop",
    "backed",
    "backer",
    "backfield",
    "backfire",
    "backhand",
    "backing",
    "backlands",
    "backlash",
    "backless",
    "backlight",
    "backlit",
    "backlog",
    "backpack",
    "backpedal",
    "backrest",
    "backroom",
    "backshift",
    "backside",
    "backslid",
    "backspace",
    "backspin",
    "backstab",
    "backstage",
    "backtalk",
    "backtrack",
    "backup",
    "backward",
    "backwash",
    "backwater",
    "backyard",
    "bacon",
    "bacteria",
    "bacterium",
    "badass",
    "badge",
    "badland",
    "badly",
    "badness",
    "baffle",
    "baffling",
    "bagel",
    "bagful",
    "baggage",
    "bagged",
    "baggie",
    "bagginess",
    "bagging",
    "baggy",
    "bagpipe",
    "baguette",
    "baked",
    "bakery",
    "bakeshop",
    "baking",
    "balance",
    "balancing",
    "balcony",
    "balmy",
    "balsamic",
    "bamboo",
    "banana",
    "banish",
    "banister",
    "banjo",
    "bankable",
    "bankbook",
    "banked",
    "banker",
    "banking",
    "banknote",
    "bankroll",
    "banner",
    "bannister",
    "banshee",
    "banter",
    "barbecue",
    "barbed",
    "barbell",
    "barber",
    "barcode",
    "barge",
    "bargraph",
    "barista",
    "baritone",
    "barley",
    "barmaid",
    "barman",
    "barn",
    "barometer",
    "barrack",
    "barracuda",
    "barrel",
    "barrette",
    "barricade",
    "barrier",
    "barstool",
    "bartender",
    "barterer",
    "bash",
    "basically",
    "basics",
    "basil",
    "basin",
    "basis",
    "basket",
    "batboy",
    "batch",
    "bath",
    "baton",
    "bats",
    "battalion",
    "battered",
    "battering",
    "battery",
    "batting",
    "battle",
    "bauble",
    "bazooka",
    "blabber",
    "bladder",
    "blade",
    "blah",
    "blame",
    "blaming",
    "blanching",
    "blandness",
    "blank",
    "blaspheme",
    "blasphemy",
    "blast",
    "blatancy",
    "blatantly",
    "blazer",
    "blazing",
    "bleach",
    "bleak",
    "bleep",
    "blemish",
    "blend",
    "bless",
    "blighted",
    "blimp",
    "bling",
    "blinked",
    "blinker",
    "blinking",
    "blinks",
    "blip",
    "blissful",
    "blitz",
    "blizzard",
    "bloated",
    "bloating",
    "blob",
    "blog",
    "bloomers",
    "blooming",
    "blooper",
    "blot",
    "blouse",
    "blubber",
    "bluff",
    "bluish",
    "blunderer",
    "blunt",
    "blurb",
    "blurred",
    "blurry",
    "blurt",
    "blush",
    "blustery",
    "boaster",
    "boastful",
    "boasting",
    "boat",
    "bobbed",
    "bobbing",
    "bobble",
    "bobcat",
    "bobsled",
    "bobtail",
    "bodacious",
    "body",
    "bogged",
    "boggle",
    "bogus",
    "boil",
    "bok",
    "bolster",
    "bolt",
    "bonanza",
    "bonded",
    "bonding",
    "bondless",
    "boned",
    "bonehead",
    "boneless",
    "bonelike",
    "boney",
    "bonfire",
    "bonnet",
    "bonsai",
    "bonus",
    "bony",
    "boogeyman",
    "boogieman",
    "book",
    "boondocks",
    "booted",
    "booth",
    "bootie",
    "booting",
    "bootlace",
    "bootleg",
    "boots",
    "boozy",
    "borax",
    "boring",
    "borough",
    "borrower",
    "borrowing",
    "boss",
    "botanical",
    "botanist",
    "botany",
    "botch",
    "both",
    "bottle",
    "bottling",
    "bottom",
    "bounce",
    "bouncing",
    "bouncy",
    "bounding",
    "boundless",
    "bountiful",
    "bovine",
    "boxcar",
    "boxer",
    "boxing",
    "boxlike",
    "boxy",
    "breach",
    "breath",
    "breeches",
    "breeching",
    "breeder",
    "breeding",
    "breeze",
    "breezy",
    "brethren",
    "brewery",
    "brewing",
    "briar",
    "bribe",
    "brick",
    "bride",
    "bridged",
    "brigade",
    "bright",
    "brilliant",
    "brim",
    "bring",
    "brink",
    "brisket",
    "briskly",
    "briskness",
    "bristle",
    "brittle",
    "broadband",
    "broadcast",
    "broaden",
    "broadly",
    "broadness",
    "broadside",
    "broadways",
    "broiler",
    "broiling",
    "broken",
    "broker",
    "bronchial",
    "bronco",
    "bronze",
    "bronzing",
    "brook",
    "broom",
    "brought",
    "browbeat",
    "brownnose",
    "browse",
    "browsing",
    "bruising",
    "brunch",
    "brunette",
    "brunt",
    "brush",
    "brussels",
    "brute",
    "brutishly",
    "bubble",
    "bubbling",
    "bubbly",
    "buccaneer",
    "bucked",
    "bucket",
    "buckle",
    "buckshot",
    "buckskin",
    "bucktooth",
    "buckwheat",
    "buddhism",
    "buddhist",
    "budding",
    "buddy",
    "budget",
    "buffalo",
    "buffed",
    "buffer",
    "buffing",
    "buffoon",
    "buggy",
    "bulb",
    "bulge",
    "bulginess",
    "bulgur",
    "bulk",
    "bulldog",
    "bulldozer",
    "bullfight",
    "bullfrog",
    "bullhorn",
    "bullion",
    "bullish",
    "bullpen",
    "bullring",
    "bullseye",
    "bullwhip",
    "bully",
    "bunch",
    "bundle",
    "bungee",
    "bunion",
    "bunkbed",
    "bunkhouse",
    "bunkmate",
    "bunny",
    "bunt",
    "busboy",
    "bush",
    "busily",
    "busload",
    "bust",
    "busybody",
    "buzz",
    "cabana",
    "cabbage",
    "cabbie",
    "cabdriver",
    "cable",
    "caboose",
    "cache",
    "cackle",
    "cacti",
    "cactus",
    "caddie",
    "caddy",
    "cadet",
    "cadillac",
    "cadmium",
    "cage",
    "cahoots",
    "cake",
    "calamari",
    "calamity",
    "calcium",
    "calculate",
    "calculus",
    "caliber",
    "calibrate",
    "calm",
    "caloric",
    "calorie",
    "calzone",
    "camcorder",
    "cameo",
    "camera",
    "camisole",
    "camper",
    "campfire",
    "camping",
    "campsite",
    "campus",
    "canal",
    "canary",
    "cancel",
    "candied",
    "candle",
    "candy",
    "cane",
    "canine",
    "canister",
    "cannabis",
    "canned",
    "canning",
    "cannon",
    "cannot",
    "canola",
    "canon",
    "canopener",
    "canopy",
    "canteen",
    "canyon",
    "capable",
    "capably",
    "capacity",
    "cape",
    "capillary",
    "capital",
    "capitol",
    "capped",
    "capricorn",
    "capsize",
    "capsule",
    "caption",
    "captivate",
    "captive",
    "captivity",
    "capture",
    "caramel",
    "carat",
    "caravan",
    "carbon",
    "cardboard",
    "carded",
    "cardiac",
    "cardigan",
    "cardinal",
    "cardstock",
    "carefully",
    "caregiver",
    "careless",
    "caress",
    "caretaker",
    "cargo",
    "caring",
    "carless",
    "carload",
    "carmaker",
    "carnage",
    "carnation",
    "carnival",
    "carnivore",
    "carol",
    "carpenter",
    "carpentry",
    "carpool",
    "carport",
    "carried",
    "carrot",
    "carrousel",
    "carry",
    "cartel",
    "cartload",
    "carton",
    "cartoon",
    "cartridge",
    "cartwheel",
    "carve",
    "carving",
    "carwash",
    "cascade",
    "case",
    "cash",
    "casing",
    "casino",
    "casket",
    "cassette",
    "casually",
    "casualty",
    "catacomb",
    "catalog",
    "catalyst",
    "catalyze",
    "catapult",
    "cataract",
    "catatonic",
    "catcall",
    "catchable",
    "catcher",
    "catching",
    "catchy",
    "caterer",
    "catering",
    "catfight",
    "catfish",
    "cathedral",
    "cathouse",
    "catlike",
    "catnap",
    "catnip",
    "catsup",
    "cattail",
    "cattishly",
    "cattle",
    "catty",
    "catwalk",
    "caucasian",
    "caucus",
    "causal",
    "causation",
    "cause",
    "causing",
    "cauterize",
    "caution",
    "cautious",
    "cavalier",
    "cavalry",
    "caviar",
    "cavity",
    "cedar",
    "celery",
    "celestial",
    "celibacy",
    "celibate",
    "celtic",
    "cement",
    "census",
    "ceramics",
    "ceremony",
    "certainly",
    "certainty",
    "certified",
    "certify",
    "cesarean",
    "cesspool",
    "chafe",
    "chaffing",
    "chain",
    "chair",
    "chalice",
    "challenge",
    "chamber",
    "chamomile",
    "champion",
    "chance",
    "change",
    "channel",
    "chant",
    "chaos",
    "chaperone",
    "chaplain",
    "chapped",
    "chaps",
    "chapter",
    "character",
    "charbroil",
    "charcoal",
    "charger",
    "charging",
    "chariot",
    "charity",
    "charm",
    "charred",
    "charter",
    "charting",
    "chase",
    "chasing",
    "chaste",
    "chastise",
    "chastity",
    "chatroom",
    "chatter",
    "chatting",
    "chatty",
    "cheating",
    "cheddar",
    "cheek",
    "cheer",
    "cheese",
    "cheesy",
    "chef",
    "chemicals",
    "chemist",
    "chemo",
    "cherisher",
    "cherub",
    "chess",
    "chest",
    "chevron",
    "chevy",
    "chewable",
    "chewer",
    "chewing",
    "chewy",
    "chief",
    "chihuahua",
    "childcare",
    "childhood",
    "childish",
    "childless",
    "childlike",
    "chili",
    "chill",
    "chimp",
    "chip",
    "chirping",
    "chirpy",
    "chitchat",
    "chivalry",
    "chive",
    "chloride",
    "chlorine",
    "choice",
    "chokehold",
    "choking",
    "chomp",
    "chooser",
    "choosing",
    "choosy",
    "chop",
    "chosen",
    "chowder",
    "chowtime",
    "chrome",
    "chubby",
    "chuck",
    "chug",
    "chummy",
    "chump",
    "chunk",
    "churn",
    "chute",
    "cider",
    "cilantro",
    "cinch",
    "cinema",
    "cinnamon",
    "circle",
    "circling",
    "circular",
    "circulate",
    "circus",
    "citable",
    "citadel",
    "citation",
    "citizen",
    "citric",
    "citrus",
    "city",
    "civic",
    "civil",
    "clad",
    "claim",
    "clambake",
    "clammy",
    "clamor",
    "clamp",
    "clamshell",
    "clang",
    "clanking",
    "clapped",
    "clapper",
    "clapping",
    "clarify",
    "clarinet",
    "clarity",
    "clash",
    "clasp",
    "class",
    "clatter",
    "clause",
    "clavicle",
    "claw",
    "clay",
    "clean",
    "clear",
    "cleat",
    "cleaver",
    "cleft",
    "clench",
    "clergyman",
    "clerical",
    "clerk",
    "clever",
    "clicker",
    "client",
    "climate",
    "climatic",
    "cling",
    "clinic",
    "clinking",
    "clip",
    "clique",
    "cloak",
    "clobber",
    "clock",
    "clone",
    "cloning",
    "closable",
    "closure",
    "clothes",
    "clothing",
    "cloud",
    "clover",
    "clubbed",
    "clubbing",
    "clubhouse",
    "clump",
    "clumsily",
    "clumsy",
    "clunky",
    "clustered",
    "clutch",
    "clutter",
    "coach",
    "coagulant",
    "coastal",
    "coaster",
    "coasting",
    "coastland",
    "coastline",
    "coat",
    "coauthor",
    "cobalt",
    "cobbler",
    "cobweb",
    "cocoa",
    "coconut",
    "cod",
    "coeditor",
    "coerce",
    "coexist",
    "coffee",
    "cofounder",
    "cognition",
    "cognitive",
    "cogwheel",
    "coherence",
    "coherent",
    "cohesive",
    "coil",
    "coke",
    "cola",
    "cold",
    "coleslaw",
    "coliseum",
    "collage",
    "collapse",
    "collar",
    "collected",
    "collector",
    "collide",
    "collie",
    "collision",
    "colonial",
    "colonist",
    "colonize",
    "colony",
    "colossal",
    "colt",
    "coma",
    "come",
    "comfort",
    "comfy",
    "comic",
    "coming",
    "comma",
    "commence",
    "commend",
    "comment",
    "commerce",
    "commode",
    "commodity",
    "commodore",
    "common",
    "commotion",
    "commute",
    "commuting",
    "compacted",
    "compacter",
    "compactly",
    "compactor",
    "companion",
    "company",
    "compare",
    "compel",
    "compile",
    "comply",
    "component",
    "composed",
    "composer",
    "composite",
    "compost",
    "composure",
    "compound",
    "compress",
    "comprised",
    "computer",
    "computing",
    "comrade",
    "concave",
    "conceal",
    "conceded",
    "concept",
    "concerned",
    "concert",
    "conch",
    "concierge",
    "concise",
    "conclude",
    "concrete",
    "concur",
    "condense",
    "condiment",
    "condition",
    "condone",
    "conducive",
    "conductor",
    "conduit",
    "cone",
    "confess",
    "confetti",
    "confidant",
    "confident",
    "confider",
    "confiding",
    "configure",
    "confined",
    "confining",
    "confirm",
    "conflict",
    "conform",
    "confound",
    "confront",
    "confused",
    "confusing",
    "confusion",
    "congenial",
    "congested",
    "congrats",
    "congress",
    "conical",
    "conjoined",
    "conjure",
    "conjuror",
    "connected",
    "connector",
    "consensus",
    "consent",
    "console",
    "consoling",
    "consonant",
    "constable",
    "constant",
    "constrain",
    "constrict",
    "construct",
    "consult",
    "consumer",
    "consuming",
    "contact",
    "container",
    "contempt",
    "contend",
    "contented",
    "contently",
    "contents",
    "contest",
    "context",
    "contort",
    "contour",
    "contrite",
    "control",
    "contusion",
    "convene",
    "convent",
    "copartner",
    "cope",
    "copied",
    "copier",
    "copilot",
    "coping",
    "copious",
    "copper",
    "copy",
    "coral",
    "cork",
    "cornball",
    "cornbread",
    "corncob",
    "cornea",
    "corned",
    "corner",
    "cornfield",
    "cornflake",
    "cornhusk",
    "cornmeal",
    "cornstalk",
    "corny",
    "coronary",
    "coroner",
    "corporal",
    "corporate",
    "corral",
    "correct",
    "corridor",
    "corrode",
    "corroding",
    "corrosive",
    "corsage",
    "corset",
    "cortex",
    "cosigner",
    "cosmetics",
    "cosmic",
    "cosmos",
    "cosponsor",
    "cost",
    "cottage",
    "cotton",
    "couch",
    "cough",
    "could",
    "countable",
    "countdown",
    "counting",
    "countless",
    "country",
    "county",
    "courier",
    "covenant",
    "cover",
    "coveted",
    "coveting",
    "coyness",
    "cozily",
    "coziness",
    "cozy",
    "crabbing",
    "crabgrass",
    "crablike",
    "crabmeat",
    "cradle",
    "cradling",
    "crafter",
    "craftily",
    "craftsman",
    "craftwork",
    "crafty",
    "cramp",
    "cranberry",
    "crane",
    "cranial",
    "cranium",
    "crank",
    "crate",
    "crave",
    "craving",
    "crawfish",
    "crawlers",
    "crawling",
    "crayfish",
    "crayon",
    "crazed",
    "crazily",
    "craziness",
    "crazy",
    "creamed",
    "creamer",
    "creamlike",
    "crease",
    "creasing",
    "creatable",
    "create",
    "creation",
    "creative",
    "creature",
    "credible",
    "credibly",
    "credit",
    "creed",
    "creme",
    "creole",
    "crepe",
    "crept",
    "crescent",
    "crested",
    "cresting",
    "crestless",
    "crevice",
    "crewless",
    "crewman",
    "crewmate",
    "crib",
    "cricket",
    "cried",
    "crier",
    "crimp",
    "crimson",
    "cringe",
    "cringing",
    "crinkle",
    "crinkly",
    "crisped",
    "crisping",
    "crisply",
    "crispness",
    "crispy",
    "criteria",
    "critter",
    "croak",
    "crock",
    "crook",
    "croon",
    "crop",
    "cross",
    "crouch",
    "crouton",
    "crowbar",
    "crowd",
    "crown",
    "crucial",
    "crudely",
    "crudeness",
    "cruelly",
    "cruelness",
    "cruelty",
    "crumb",
    "crummiest",
    "crummy",
    "crumpet",
    "crumpled",
    "cruncher",
    "crunching",
    "crunchy",
    "crusader",
    "crushable",
    "crushed",
    "crusher",
    "crushing",
    "crust",
    "crux",
    "crying",
    "cryptic",
    "crystal",
    "cubbyhole",
    "cube",
    "cubical",
    "cubicle",
    "cucumber",
    "cuddle",
    "cuddly",
    "cufflink",
    "culinary",
    "culminate",
    "culpable",
    "culprit",
    "cultivate",
    "cultural",
    "culture",
    "cupbearer",
    "cupcake",
    "cupid",
    "cupped",
    "cupping",
    "curable",
    "curator",
    "curdle",
    "cure",
    "curfew",
    "curing",
    "curled",
    "curler",
    "curliness",
    "curling",
    "curly",
    "curry",
    "curse",
    "cursive",
    "cursor",
    "curtain",
    "curtly",
    "curtsy",
    "curvature",
    "curve",
    "curvy",
    "cushy",
    "cusp",
    "cussed",
    "custard",
    "custodian",
    "custody",
    "customary",
    "customer",
    "customize",
    "customs",
    "cut",
    "cycle",
    "cyclic",
    "cycling",
    "cyclist",
    "cylinder",
    "cymbal",
    "cytoplasm",
    "cytoplast",
    "dab",
    "dad",
    "daffodil",
    "dagger",
    "daily",
    "daintily",
    "dainty",
    "dairy",
    "daisy",
    "dallying",
    "dance",
    "dancing",
    "dandelion",
    "dander",
    "dandruff",
    "dandy",
    "danger",
    "dangle",
    "dangling",
    "daredevil",
    "dares",
    "daringly",
    "darkened",
    "darkening",
    "darkish",
    "darkness",
    "darkroom",
    "darling",
    "darn",
    "dart",
    "darwinism",
    "dash",
    "dastardly",
    "data",
    "datebook",
    "dating",
    "daughter",
    "daunting",
    "dawdler",
    "dawn",
    "daybed",
    "daybreak",
    "daycare",
    "daydream",
    "daylight",
    "daylong",
    "dayroom",
    "daytime",
    "dazzler",
    "dazzling",
    "deacon",
    "deafening",
    "deafness",
    "dealer",
    "dealing",
    "dealmaker",
    "dealt",
    "dean",
    "debatable",
    "debate",
    "debating",
    "debit",
    "debrief",
    "debtless",
    "debtor",
    "debug",
    "debunk",
    "decade",
    "decaf",
    "decal",
    "decathlon",
    "decay",
    "deceased",
    "deceit",
    "deceiver",
    "deceiving",
    "december",
    "decency",
    "decent",
    "deception",
    "deceptive",
    "decibel",
    "decidable",
    "decimal",
    "decimeter",
    "decipher",
    "deck",
    "declared",
    "decline",
    "decode",
    "decompose",
    "decorated",
    "decorator",
    "decoy",
    "decrease",
    "decree",
    "dedicate",
    "dedicator",
    "deduce",
    "deduct",
    "deed",
    "deem",
    "deepen",
    "deeply",
    "deepness",
    "deface",
    "defacing",
    "defame",
    "default",
    "defeat",
    "defection",
    "defective",
    "defendant",
    "defender",
    "defense",
    "defensive",
    "deferral",
    "deferred",
    "defiance",
    "defiant",
    "defile",
    "defiling",
    "define",
    "definite",
    "deflate",
    "deflation",
    "deflator",
    "deflected",
    "deflector",
    "defog",
    "deforest",
    "defraud",
    "defrost",
    "deftly",
    "defuse",
    "defy",
    "degraded",
    "degrading",
    "degrease",
    "degree",
    "dehydrate",
    "deity",
    "dejected",
    "delay",
    "delegate",
    "delegator",
    "delete",
    "deletion",
    "delicacy",
    "delicate",
    "delicious",
    "delighted",
    "delirious",
    "delirium",
    "deliverer",
    "delivery",
    "delouse",
    "delta",
    "deluge",
    "delusion",
    "deluxe",
    "demanding",
    "demeaning",
    "demeanor",
    "demise",
    "democracy",
    "democrat",
    "demote",
    "demotion",
    "demystify",
    "denatured",
    "deniable",
    "denial",
    "denim",
    "denote",
    "dense",
    "density",
    "dental",
    "dentist",
    "denture",
    "deny",
    "deodorant",
    "deodorize",
    "departed",
    "departure",
    "depict",
    "deplete",
    "depletion",
    "deplored",
    "deploy",
    "deport",
    "depose",
    "depraved",
    "depravity",
    "deprecate",
    "depress",
    "deprive",
    "depth",
    "deputize",
    "deputy",
    "derail",
    "deranged",
    "derby",
    "derived",
    "desecrate",
    "deserve",
    "deserving",
    "designate",
    "designed",
    "designer",
    "designing",
    "deskbound",
    "desktop",
    "deskwork",
    "desolate",
    "despair",
    "despise",
    "despite",
    "destiny",
    "destitute",
    "destruct",
    "detached",
    "detail",
    "detection",
    "detective",
    "detector",
    "detention",
    "detergent",
    "detest",
    "detonate",
    "detonator",
    "detoxify",
    "detract",
    "deuce",
    "devalue",
    "deviancy",
    "deviant",
    "deviate",
    "deviation",
    "deviator",
    "device",
    "devious",
    "devotedly",
    "devotee",
    "devotion",
    "devourer",
    "devouring",
    "devoutly",
    "dexterity",
    "dexterous",
    "diabetes",
    "diabetic",
    "diabolic",
    "diagnoses",
    "diagnosis",
    "diagram",
    "dial",
    "diameter",
    "diaper",
    "diaphragm",
    "diary",
    "dice",
    "dicing",
    "dictate",
    "dictation",
    "dictator",
    "difficult",
    "diffused",
    "diffuser",
    "diffusion",
    "diffusive",
    "dig",
    "dilation",
    "diligence",
    "diligent",
    "dill",
    "dilute",
    "dime",
    "diminish",
    "dimly",
    "dimmed",
    "dimmer",
    "dimness",
    "dimple",
    "diner",
    "dingbat",
    "dinghy",
    "dinginess",
    "dingo",
    "dingy",
    "dining",
    "dinner",
    "diocese",
    "dioxide",
    "diploma",
    "dipped",
    "dipper",
    "dipping",
    "directed",
    "direction",
    "directive",
    "directly",
    "directory",
    "direness",
    "dirtiness",
    "disabled",
    "disagree",
    "disallow",
    "disarm",
    "disarray",
    "disaster",
    "disband",
    "disbelief",
    "disburse",
    "discard",
    "discern",
    "discharge",
    "disclose",
    "discolor",
    "discount",
    "discourse",
    "discover",
    "discuss",
    "disdain",
    "disengage",
    "disfigure",
    "disgrace",
    "dish",
    "disinfect",
    "disjoin",
    "disk",
    "dislike",
    "disliking",
    "dislocate",
    "dislodge",
    "disloyal",
    "dismantle",
    "dismay",
    "dismiss",
    "dismount",
    "disobey",
    "disorder",
    "disown",
    "disparate",
    "disparity",
    "dispatch",
    "dispense",
    "dispersal",
    "dispersed",
    "disperser",
    "displace",
    "display",
    "displease",
    "disposal",
    "dispose",
    "disprove",
    "dispute",
    "disregard",
    "disrupt",
    "dissuade",
    "distance",
    "distant",
    "distaste",
    "distill",
    "distinct",
    "distort",
    "distract",
    "distress",
    "district",
    "distrust",
    "ditch",
    "ditto",
    "ditzy",
    "dividable",
    "divided",
    "dividend",
    "dividers",
    "dividing",
    "divinely",
    "diving",
    "divinity",
    "divisible",
    "divisibly",
    "division",
    "divisive",
    "divorcee",
    "dizziness",
    "dizzy",
    "doable",
    "docile",
    "dock",
    "doctrine",
    "document",
    "dodge",
    "dodgy",
    "doily",
    "doing",
    "dole",
    "dollar",
    "dollhouse",
    "dollop",
    "dolly",
    "dolphin",
    "domain",
    "domelike",
    "domestic",
    "dominion",
    "dominoes",
    "donated",
    "donation",
    "donator",
    "donor",
    "donut",
    "doodle",
    "doorbell",
    "doorframe",
    "doorknob",
    "doorman",
    "doormat",
    "doornail",
    "doorpost",
    "doorstep",
    "doorstop",
    "doorway",
    "doozy",
    "dork",
    "dormitory",
    "dorsal",
    "dosage",
    "dose",
    "dotted",
    "doubling",
    "douche",
    "dove",
    "down",
    "dowry",
    "doze",
    "drab",
    "dragging",
    "dragonfly",
    "dragonish",
    "dragster",
    "drainable",
    "drainage",
    "drained",
    "drainer",
    "drainpipe",
    "dramatic",
    "dramatize",
    "drank",
    "drapery",
    "drastic",
    "draw",
    "dreaded",
    "dreadful",
    "dreadlock",
    "dreamboat",
    "dreamily",
    "dreamland",
    "dreamless",
    "dreamlike",
    "dreamt",
    "dreamy",
    "drearily",
    "dreary",
    "drench",
    "dress",
    "drew",
    "dribble",
    "dried",
    "drier",
    "drift",
    "driller",
    "drilling",
    "drinkable",
    "drinking",
    "dripping",
    "drippy",
    "drivable",
    "driven",
    "driver",
    "driveway",
    "driving",
    "drizzle",
    "drizzly",
    "drone",
    "drool",
    "droop",
    "drop-down",
    "dropbox",
    "dropkick",
    "droplet",
    "dropout",
    "dropper",
    "drove",
    "drown",
    "drowsily",
    "drudge",
    "drum",
    "dry",
    "dubbed",
    "dubiously",
    "duchess",
    "duckbill",
    "ducking",
    "duckling",
    "ducktail",
    "ducky",
    "duct",
    "dude",
    "duffel",
    "dugout",
    "duh",
    "duke",
    "duller",
    "dullness",
    "duly",
    "dumping",
    "dumpling",
    "dumpster",
    "duo",
    "dupe",
    "duplex",
    "duplicate",
    "duplicity",
    "durable",
    "durably",
    "duration",
    "duress",
    "during",
    "dusk",
    "dust",
    "dutiful",
    "duty",
    "duvet",
    "dwarf",
    "dweeb",
    "dwelled",
    "dweller",
    "dwelling",
    "dwindle",
    "dwindling",
    "dynamic",
    "dynamite",
    "dynasty",
    "dyslexia",
    "dyslexic",
    "each",
    "eagle",
    "earache",
    "eardrum",
    "earflap",
    "earful",
    "earlobe",
    "early",
    "earmark",
    "earmuff",
    "earphone",
    "earpiece",
    "earplugs",
    "earring",
    "earshot",
    "earthen",
    "earthlike",
    "earthling",
    "earthly",
    "earthworm",
    "earthy",
    "earwig",
    "easeful",
    "easel",
    "easiest",
    "easily",
    "easiness",
    "easing",
    "eastbound",
    "eastcoast",
    "easter",
    "eastward",
    "eatable",
    "eaten",
    "eatery",
    "eating",
    "eats",
    "ebay",
    "ebony",
    "ebook",
    "ecard",
    "eccentric",
    "echo",
    "eclair",
    "eclipse",
    "ecologist",
    "ecology",
    "economic",
    "economist",
    "economy",
    "ecosphere",
    "ecosystem",
    "edge",
    "edginess",
    "edging",
    "edgy",
    "edition",
    "editor",
    "educated",
    "education",
    "educator",
    "eel",
    "effective",
    "effects",
    "efficient",
    "effort",
    "eggbeater",
    "egging",
    "eggnog",
    "eggplant",
    "eggshell",
    "egomaniac",
    "egotism",
    "egotistic",
    "either",
    "eject",
    "elaborate",
    "elastic",
    "elated",
    "elbow",
    "eldercare",
    "elderly",
    "eldest",
    "electable",
    "election",
    "elective",
    "elephant",
    "elevate",
    "elevating",
    "elevation",
    "elevator",
    "eleven",
    "elf",
    "eligible",
    "eligibly",
    "eliminate",
    "elite",
    "elitism",
    "elixir",
    "elk",
    "ellipse",
    "elliptic",
    "elm",
    "elongated",
    "elope",
    "eloquence",
    "eloquent",
    "elsewhere",
    "elude",
    "elusive",
    "elves",
    "email",
    "embargo",
    "embark",
    "embassy",
    "embattled",
    "embellish",
    "ember",
    "embezzle",
    "emblaze",
    "emblem",
    "embody",
    "embolism",
    "emboss",
    "embroider",
    "emcee",
    "emerald",
    "emergency",
    "emission",
    "emit",
    "emote",
    "emoticon",
    "emotion",
    "empathic",
    "empathy",
    "emperor",
    "emphases",
    "emphasis",
    "emphasize",
    "emphatic",
    "empirical",
    "employed",
    "employee",
    "employer",
    "emporium",
    "empower",
    "emptier",
    "emptiness",
    "empty",
    "emu",
    "enable",
    "enactment",
    "enamel",
    "enchanted",
    "enchilada",
    "encircle",
    "enclose",
    "enclosure",
    "encode",
    "encore",
    "encounter",
    "encourage",
    "encroach",
    "encrust",
    "encrypt",
    "endanger",
    "endeared",
    "endearing",
    "ended",
    "ending",
    "endless",
    "endnote",
    "endocrine",
    "endorphin",
    "endorse",
    "endowment",
    "endpoint",
    "endurable",
    "endurance",
    "enduring",
    "energetic",
    "energize",
    "energy",
    "enforced",
    "enforcer",
    "engaged",
    "engaging",
    "engine",
    "engorge",
    "engraved",
    "engraver",
    "engraving",
    "engross",
    "engulf",
    "enhance",
    "enigmatic",
    "enjoyable",
    "enjoyably",
    "enjoyer",
    "enjoying",
    "enjoyment",
    "enlarged",
    "enlarging",
    "enlighten",
    "enlisted",
    "enquirer",
    "enrage",
    "enrich",
    "enroll",
    "enslave",
    "ensnare",
    "ensure",
    "entail",
    "entangled",
    "entering",
    "entertain",
    "enticing",
    "entire",
    "entitle",
    "entity",
    "entomb",
    "entourage",
    "entrap",
    "entree",
    "entrench",
    "entrust",
    "entryway",
    "entwine",
    "enunciate",
    "envelope",
    "enviable",
    "enviably",
    "envious",
    "envision",
    "envoy",
    "envy",
    "enzyme",
    "epic",
    "epidemic",
    "epidermal",
    "epidermis",
    "epidural",
    "epilepsy",
    "epileptic",
    "epilogue",
    "epiphany",
    "episode",
    "equal",
    "equate",
    "equation",
    "equator",
    "equinox",
    "equipment",
    "equity",
    "equivocal",
    "eradicate",
    "erasable",
    "erased",
    "eraser",
    "erasure",
    "ergonomic",
    "errand",
    "errant",
    "erratic",
    "error",
    "erupt",
    "escalate",
    "escalator",
    "escapable",
    "escapade",
    "escapist",
    "escargot",
    "eskimo",
    "esophagus",
    "espionage",
    "espresso",
    "esquire",
    "essay",
    "essence",
    "essential",
    "establish",
    "estate",
    "esteemed",
    "estimate",
    "estimator",
    "estranged",
    "estrogen",
    "etching",
    "eternal",
    "eternity",
    "ethanol",
    "ether",
    "ethically",
    "ethics",
    "euphemism",
    "evacuate",
    "evacuee",
    "evade",
    "evaluate",
    "evaluator",
    "evaporate",
    "evasion",
    "evasive",
    "even",
    "everglade",
    "evergreen",
    "everybody",
    "everyday",
    "everyone",
    "evict",
    "evidence",
    "evident",
    "evil",
    "evoke",
    "evolution",
    "evolve",
    "exact",
    "exalted",
    "example",
    "excavate",
    "excavator",
    "exceeding",
    "exception",
    "excess",
    "exchange",
    "excitable",
    "exciting",
    "exclaim",
    "exclude",
    "excluding",
    "exclusion",
    "exclusive",
    "excretion",
    "excretory",
    "excursion",
    "excusable",
    "excusably",
    "excuse",
    "exemplary",
    "exemplify",
    "exemption",
    "exerciser",
    "exert",
    "exes",
    "exfoliate",
    "exhale",
    "exhaust",
    "exhume",
    "exile",
    "existing",
    "exit",
    "exodus",
    "exonerate",
    "exorcism",
    "exorcist",
    "expand",
    "expanse",
    "expansion",
    "expansive",
    "expectant",
    "expedited",
    "expediter",
    "expel",
    "expend",
    "expenses",
    "expensive",
    "expert",
    "expire",
    "expiring",
    "explain",
    "expletive",
    "explicit",
    "explode",
    "exploit",
    "explore",
    "exploring",
    "exponent",
    "exporter",
    "exposable",
    "expose",
    "exposure",
    "express",
    "expulsion",
    "exquisite",
    "extended",
    "extending",
    "extent",
    "extenuate",
    "exterior",
    "external",
    "extinct",
    "extortion",
    "extradite",
    "extras",
    "extrovert",
    "extrude",
    "extruding",
    "exuberant",
    "fable",
    "fabric",
    "fabulous",
    "facebook",
    "facecloth",
    "facedown",
    "faceless",
    "facelift",
    "faceplate",
    "faceted",
    "facial",
    "facility",
    "facing",
    "facsimile",
    "faction",
    "factoid",
    "factor",
    "factsheet",
    "factual",
    "faculty",
    "fade",
    "fading",
    "failing",
    "falcon",
    "fall",
    "false",
    "falsify",
    "fame",
    "familiar",
    "family",
    "famine",
    "famished",
    "fanatic",
    "fancied",
    "fanciness",
    "fancy",
    "fanfare",
    "fang",
    "fanning",
    "fantasize",
    "fantastic",
    "fantasy",
    "fascism",
    "fastball",
    "faster",
    "fasting",
    "fastness",
    "faucet",
    "favorable",
    "favorably",
    "favored",
    "favoring",
    "favorite",
    "fax",
    "feast",
    "federal",
    "fedora",
    "feeble",
    "feed",
    "feel",
    "feisty",
    "feline",
    "felt-tip",
    "feminine",
    "feminism",
    "feminist",
    "feminize",
    "femur",
    "fence",
    "fencing",
    "fender",
    "ferment",
    "fernlike",
    "ferocious",
    "ferocity",
    "ferret",
    "ferris",
    "ferry",
    "fervor",
    "fester",
    "festival",
    "festive",
    "festivity",
    "fetal",
    "fetch",
    "fever",
    "fiber",
    "fiction",
    "fiddle",
    "fiddling",
    "fidelity",
    "fidgeting",
    "fidgety",
    "fifteen",
    "fifth",
    "fiftieth",
    "fifty",
    "figment",
    "figure",
    "figurine",
    "filing",
    "filled",
    "filler",
    "filling",
    "film",
    "filter",
    "filth",
    "filtrate",
    "finale",
    "finalist",
    "finalize",
    "finally",
    "finance",
    "financial",
    "finch",
    "fineness",
    "finer",
    "finicky",
    "finished",
    "finisher",
    "finishing",
    "finite",
    "finless",
    "finlike",
    "fiscally",
    "fit",
    "five",
    "flaccid",
    "flagman",
    "flagpole",
    "flagship",
    "flagstick",
    "flagstone",
    "flail",
    "flakily",
    "flaky",
    "flame",
    "flammable",
    "flanked",
    "flanking",
    "flannels",
    "flap",
    "flaring",
    "flashback",
    "flashbulb",
    "flashcard",
    "flashily",
    "flashing",
    "flashy",
    "flask",
    "flatbed",
    "flatfoot",
    "flatly",
    "flatness",
    "flatten",
    "flattered",
    "flatterer",
    "flattery",
    "flattop",
    "flatware",
    "flatworm",
    "flavored",
    "flavorful",
    "flavoring",
    "flaxseed",
    "fled",
    "fleshed",
    "fleshy",
    "flick",
    "flier",
    "flight",
    "flinch",
    "fling",
    "flint",
    "flip",
    "flirt",
    "float",
    "flock",
    "flogging",
    "flop",
    "floral",
    "florist",
    "floss",
    "flounder",
    "flyable",
    "flyaway",
    "flyer",
    "flying",
    "flyover",
    "flypaper",
    "foam",
    "foe",
    "fog",
    "foil",
    "folic",
    "folk",
    "follicle",
    "follow",
    "fondling",
    "fondly",
    "fondness",
    "fondue",
    "font",
    "food",
    "fool",
    "footage",
    "football",
    "footbath",
    "footboard",
    "footer",
    "footgear",
    "foothill",
    "foothold",
    "footing",
    "footless",
    "footman",
    "footnote",
    "footpad",
    "footpath",
    "footprint",
    "footrest",
    "footsie",
    "footsore",
    "footwear",
    "footwork",
    "fossil",
    "foster",
    "founder",
    "founding",
    "fountain",
    "fox",
    "foyer",
    "fraction",
    "fracture",
    "fragile",
    "fragility",
    "fragment",
    "fragrance",
    "fragrant",
    "frail",
    "frame",
    "framing",
    "frantic",
    "fraternal",
    "frayed",
    "fraying",
    "frays",
    "freckled",
    "freckles",
    "freebase",
    "freebee",
    "freebie",
    "freedom",
    "freefall",
    "freehand",
    "freeing",
    "freeload",
    "freely",
    "freemason",
    "freeness",
    "freestyle",
    "freeware",
    "freeway",
    "freewill",
    "freezable",
    "freezing",
    "freight",
    "french",
    "frenzied",
    "frenzy",
    "frequency",
    "frequent",
    "fresh",
    "fretful",
    "fretted",
    "friction",
    "friday",
    "fridge",
    "fried",
    "friend",
    "frighten",
    "frightful",
    "frigidity",
    "frigidly",
    "frill",
    "fringe",
    "frisbee",
    "frisk",
    "fritter",
    "frivolous",
    "frolic",
    "from",
    "front",
    "frostbite",
    "frosted",
    "frostily",
    "frosting",
    "frostlike",
    "frosty",
    "froth",
    "frown",
    "frozen",
    "fructose",
    "frugality",
    "frugally",
    "fruit",
    "frustrate",
    "frying",
    "gab",
    "gaffe",
    "gag",
    "gainfully",
    "gaining",
    "gains",
    "gala",
    "gallantly",
    "galleria",
    "gallery",
    "galley",
    "gallon",
    "gallows",
    "gallstone",
    "galore",
    "galvanize",
    "gambling",
    "game",
    "gaming",
    "gamma",
    "gander",
    "gangly",
    "gangrene",
    "gangway",
    "gap",
    "garage",
    "garbage",
    "garden",
    "gargle",
    "garland",
    "garlic",
    "garment",
    "garnet",
    "garnish",
    "garter",
    "gas",
    "gatherer",
    "gathering",
    "gating",
    "gauging",
    "gauntlet",
    "gauze",
    "gave",
    "gawk",
    "gazing",
    "gear",
    "gecko",
    "geek",
    "geiger",
    "gem",
    "gender",
    "generic",
    "generous",
    "genetics",
    "genre",
    "gentile",
    "gentleman",
    "gently",
    "gents",
    "geography",
    "geologic",
    "geologist",
    "geology",
    "geometric",
    "geometry",
    "geranium",
    "gerbil",
    "geriatric",
    "germicide",
    "germinate",
    "germless",
    "germproof",
    "gestate",
    "gestation",
    "gesture",
    "getaway",
    "getting",
    "getup",
    "giant",
    "gibberish",
    "giblet",
    "giddily",
    "giddiness",
    "giddy",
    "gift",
    "gigabyte",
    "gigahertz",
    "gigantic",
    "giggle",
    "giggling",
    "giggly",
    "gigolo",
    "gilled",
    "gills",
    "gimmick",
    "girdle",
    "giveaway",
    "given",
    "giver",
    "giving",
    "gizmo",
    "gizzard",
    "glacial",
    "glacier",
    "glade",
    "gladiator",
    "gladly",
    "glamorous",
    "glamour",
    "glance",
    "glancing",
    "glandular",
    "glare",
    "glaring",
    "glass",
    "glaucoma",
    "glazing",
    "gleaming",
    "gleeful",
    "glider",
    "gliding",
    "glimmer",
    "glimpse",
    "glisten",
    "glitch",
    "glitter",
    "glitzy",
    "gloater",
    "gloating",
    "gloomily",
    "gloomy",
    "glorified",
    "glorifier",
    "glorify",
    "glorious",
    "glory",
    "gloss",
    "glove",
    "glowing",
    "glowworm",
    "glucose",
    "glue",
    "gluten",
    "glutinous",
    "glutton",
    "gnarly",
    "gnat",
    "goal",
    "goatskin",
    "goes",
    "goggles",
    "going",
    "goldfish",
    "goldmine",
    "goldsmith",
    "golf",
    "goliath",
    "gonad",
    "gondola",
    "gone",
    "gong",
    "good",
    "gooey",
    "goofball",
    "goofiness",
    "goofy",
    "google",
    "goon",
    "gopher",
    "gore",
    "gorged",
    "gorgeous",
    "gory",
    "gosling",
    "gossip",
    "gothic",
    "gotten",
    "gout",
    "gown",
    "grab",
    "graceful",
    "graceless",
    "gracious",
    "gradation",
    "graded",
    "grader",
    "gradient",
    "grading",
    "gradually",
    "graduate",
    "graffiti",
    "grafted",
    "grafting",
    "grain",
    "granddad",
    "grandkid",
    "grandly",
    "grandma",
    "grandpa",
    "grandson",
    "granite",
    "granny",
    "granola",
    "grant",
    "granular",
    "grape",
    "graph",
    "grapple",
    "grappling",
    "grasp",
    "grass",
    "gratified",
    "gratify",
    "grating",
    "gratitude",
    "gratuity",
    "gravel",
    "graveness",
    "graves",
    "graveyard",
    "gravitate",
    "gravity",
    "gravy",
    "gray",
    "grazing",
    "greasily",
    "greedily",
    "greedless",
    "greedy",
    "green",
    "greeter",
    "greeting",
    "grew",
    "greyhound",
    "grid",
    "grief",
    "grievance",
    "grieving",
    "grievous",
    "grill",
    "grimace",
    "grimacing",
    "grime",
    "griminess",
    "grimy",
    "grinch",
    "grinning",
    "grip",
    "gristle",
    "grit",
    "groggily",
    "groggy",
    "groin",
    "groom",
    "groove",
    "grooving",
    "groovy",
    "grope",
    "ground",
    "grouped",
    "grout",
    "grove",
    "grower",
    "growing",
    "growl",
    "grub",
    "grudge",
    "grudging",
    "grueling",
    "gruffly",
    "grumble",
    "grumbling",
    "grumbly",
    "grumpily",
    "grunge",
    "grunt",
    "guacamole",
    "guidable",
    "guidance",
    "guide",
    "guiding",
    "guileless",
    "guise",
    "gulf",
    "gullible",
    "gully",
    "gulp",
    "gumball",
    "gumdrop",
    "gumminess",
    "gumming",
    "gummy",
    "gurgle",
    "gurgling",
    "guru",
    "gush",
    "gusto",
    "gusty",
    "gutless",
    "guts",
    "gutter",
    "guy",
    "guzzler",
    "gyration",
    "habitable",
    "habitant",
    "habitat",
    "habitual",
    "hacked",
    "hacker",
    "hacking",
    "hacksaw",
    "had",
    "haggler",
    "haiku",
    "half",
    "halogen",
    "halt",
    "halved",
    "halves",
    "hamburger",
    "hamlet",
    "hammock",
    "hamper",
    "hamster",
    "hamstring",
    "handbag",
    "handball",
    "handbook",
    "handbrake",
    "handcart",
    "handclap",
    "handclasp",
    "handcraft",
    "handcuff",
    "handed",
    "handful",
    "handgrip",
    "handgun",
    "handheld",
    "handiness",
    "handiwork",
    "handlebar",
    "handled",
    "handler",
    "handling",
    "handmade",
    "handoff",
    "handpick",
    "handprint",
    "handrail",
    "handsaw",
    "handset",
    "handsfree",
    "handshake",
    "handstand",
    "handwash",
    "handwork",
    "handwoven",
    "handwrite",
    "handyman",
    "hangnail",
    "hangout",
    "hangover",
    "hangup",
    "hankering",
    "hankie",
    "hanky",
    "haphazard",
    "happening",
    "happier",
    "happiest",
    "happily",
    "happiness",
    "happy",
    "harbor",
    "hardcopy",
    "hardcore",
    "hardcover",
    "harddisk",
    "hardened",
    "hardener",
    "hardening",
    "hardhat",
    "hardhead",
    "hardiness",
    "hardly",
    "hardness",
    "hardship",
    "hardware",
    "hardwired",
    "hardwood",
    "hardy",
    "harmful",
    "harmless",
    "harmonica",
    "harmonics",
    "harmonize",
    "harmony",
    "harness",
    "harpist",
    "harsh",
    "harvest",
    "hash",
    "hassle",
    "haste",
    "hastily",
    "hastiness",
    "hasty",
    "hatbox",
    "hatchback",
    "hatchery",
    "hatchet",
    "hatching",
    "hatchling",
    "hate",
    "hatless",
    "hatred",
    "haunt",
    "haven",
    "hazard",
    "hazelnut",
    "hazily",
    "haziness",
    "hazing",
    "hazy",
    "headache",
    "headband",
    "headboard",
    "headcount",
    "headdress",
    "headed",
    "header",
    "headfirst",
    "headgear",
    "heading",
    "headlamp",
    "headless",
    "headlock",
    "headphone",
    "headpiece",
    "headrest",
    "headroom",
    "headscarf",
    "headset",
    "headsman",
    "headstand",
    "headstone",
    "headway",
    "headwear",
    "heap",
    "heat",
    "heave",
    "heavily",
    "heaviness",
    "heaving",
    "hedge",
    "hedging",
    "heftiness",
    "hefty",
    "helium",
    "helmet",
    "helper",
    "helpful",
    "helping",
    "helpless",
    "helpline",
    "hemlock",
    "hemstitch",
    "hence",
    "henchman",
    "henna",
    "herald",
    "herbal",
    "herbicide",
    "herbs",
    "heritage",
    "hermit",
    "heroics",
    "heroism",
    "herring",
    "herself",
    "hertz",
    "hesitancy",
    "hesitant",
    "hesitate",
    "hexagon",
    "hexagram",
    "hubcap",
    "huddle",
    "huddling",
    "huff",
    "hug",
    "hula",
    "hulk",
    "hull",
    "human",
    "humble",
    "humbling",
    "humbly",
    "humid",
    "humiliate",
    "humility",
    "humming",
    "hummus",
    "humongous",
    "humorist",
    "humorless",
    "humorous",
    "humpback",
    "humped",
    "humvee",
    "hunchback",
    "hundredth",
    "hunger",
    "hungrily",
    "hungry",
    "hunk",
    "hunter",
    "hunting",
    "huntress",
    "huntsman",
    "hurdle",
    "hurled",
    "hurler",
    "hurling",
    "hurray",
    "hurricane",
    "hurried",
    "hurry",
    "hurt",
    "husband",
    "hush",
    "husked",
    "huskiness",
    "hut",
    "hybrid",
    "hydrant",
    "hydrated",
    "hydration",
    "hydrogen",
    "hydroxide",
    "hyperlink",
    "hypertext",
    "hyphen",
    "hypnoses",
    "hypnosis",
    "hypnotic",
    "hypnotism",
    "hypnotist",
    "hypnotize",
    "hypocrisy",
    "hypocrite",
    "ibuprofen",
    "ice",
    "iciness",
    "icing",
    "icky",
    "icon",
    "icy",
    "idealism",
    "idealist",
    "idealize",
    "ideally",
    "idealness",
    "identical",
    "identify",
    "identity",
    "ideology",
    "idiocy",
    "idiom",
    "idly",
    "igloo",
    "ignition",
    "ignore",
    "iguana",
    "illicitly",
    "illusion",
    "illusive",
    "image",
    "imaginary",
    "imagines",
    "imaging",
    "imbecile",
    "imitate",
    "imitation",
    "immature",
    "immerse",
    "immersion",
    "imminent",
    "immobile",
    "immodest",
    "immorally",
    "immortal",
    "immovable",
    "immovably",
    "immunity",
    "immunize",
    "impaired",
    "impale",
    "impart",
    "impatient",
    "impeach",
    "impeding",
    "impending",
    "imperfect",
    "imperial",
    "impish",
    "implant",
    "implement",
    "implicate",
    "implicit",
    "implode",
    "implosion",
    "implosive",
    "imply",
    "impolite",
    "important",
    "importer",
    "impose",
    "imposing",
    "impotence",
    "impotency",
    "impotent",
    "impound",
    "imprecise",
    "imprint",
    "imprison",
    "impromptu",
    "improper",
    "improve",
    "improving",
    "improvise",
    "imprudent",
    "impulse",
    "impulsive",
    "impure",
    "impurity",
    "iodine",
    "iodize",
    "ion",
    "ipad",
    "iphone",
    "ipod",
    "irate",
    "irk",
    "iron",
    "irregular",
    "irrigate",
    "irritable",
    "irritably",
    "irritant",
    "irritate",
    "islamic",
    "islamist",
    "isolated",
    "isolating",
    "isolation",
    "isotope",
    "issue",
    "issuing",
    "italicize",
    "italics",
    "item",
    "itinerary",
    "itunes",
    "ivory",
    "ivy",
    "jab",
    "jackal",
    "jacket",
    "jackknife",
    "jackpot",
    "jailbird",
    "jailbreak",
    "jailer",
    "jailhouse",
    "jalapeno",
    "jam",
    "janitor",
    "january",
    "jargon",
    "jarring",
    "jasmine",
    "jaundice",
    "jaunt",
    "java",
    "jawed",
    "jawless",
    "jawline",
    "jaws",
    "jaybird",
    "jaywalker",
    "jazz",
    "jeep",
    "jeeringly",
    "jellied",
    "jelly",
    "jersey",
    "jester",
    "jet",
    "jiffy",
    "jigsaw",
    "jimmy",
    "jingle",
    "jingling",
    "jinx",
    "jitters",
    "jittery",
    "job",
    "jockey",
    "jockstrap",
    "jogger",
    "jogging",
    "john",
    "joining",
    "jokester",
    "jokingly",
    "jolliness",
    "jolly",
    "jolt",
    "jot",
    "jovial",
    "joyfully",
    "joylessly",
    "joyous",
    "joyride",
    "joystick",
    "jubilance",
    "jubilant",
    "judge",
    "judgingly",
    "judicial",
    "judiciary",
    "judo",
    "juggle",
    "juggling",
    "jugular",
    "juice",
    "juiciness",
    "juicy",
    "jujitsu",
    "jukebox",
    "july",
    "jumble",
    "jumbo",
    "jump",
    "junction",
    "juncture",
    "june",
    "junior",
    "juniper",
    "junkie",
    "junkman",
    "junkyard",
    "jurist",
    "juror",
    "jury",
    "justice",
    "justifier",
    "justify",
    "justly",
    "justness",
    "juvenile",
    "kabob",
    "kangaroo",
    "karaoke",
    "karate",
    "karma",
    "kebab",
    "keenly",
    "keenness",
    "keep",
    "keg",
    "kelp",
    "kennel",
    "kept",
    "kerchief",
    "kerosene",
    "kettle",
    "kick",
    "kiln",
    "kilobyte",
    "kilogram",
    "kilometer",
    "kilowatt",
    "kilt",
    "kimono",
    "kindle",
    "kindling",
    "kindly",
    "kindness",
    "kindred",
    "kinetic",
    "kinfolk",
    "king",
    "kinship",
    "kinsman",
    "kinswoman",
    "kissable",
    "kisser",
    "kissing",
    "kitchen",
    "kite",
    "kitten",
    "kitty",
    "kiwi",
    "kleenex",
    "knapsack",
    "knee",
    "knelt",
    "knickers",
    "knoll",
    "koala",
    "kooky",
    "kosher",
    "krypton",
    "kudos",
    "kung",
    "labored",
    "laborer",
    "laboring",
    "laborious",
    "labrador",
    "ladder",
    "ladies",
    "ladle",
    "ladybug",
    "ladylike",
    "lagged",
    "lagging",
    "lagoon",
    "lair",
    "lake",
    "lance",
    "landed",
    "landfall",
    "landfill",
    "landing",
    "landlady",
    "landless",
    "landline",
    "landlord",
    "landmark",
    "landmass",
    "landmine",
    "landowner",
    "landscape",
    "landside",
    "landslide",
    "language",
    "lankiness",
    "lanky",
    "lantern",
    "lapdog",
    "lapel",
    "lapped",
    "lapping",
    "laptop",
    "lard",
    "large",
    "lark",
    "lash",
    "lasso",
    "last",
    "latch",
    "late",
    "lather",
    "latitude",
    "latrine",
    "latter",
    "latticed",
    "launch",
    "launder",
    "laundry",
    "laurel",
    "lavender",
    "lavish",
    "laxative",
    "lazily",
    "laziness",
    "lazy",
    "lecturer",
    "left",
    "legacy",
    "legal",
    "legend",
    "legged",
    "leggings",
    "legible",
    "legibly",
    "legislate",
    "lego",
    "legroom",
    "legume",
    "legwarmer",
    "legwork",
    "lemon",
    "lend",
    "length",
    "lens",
    "lent",
    "leotard",
    "lesser",
    "letdown",
    "lethargic",
    "lethargy",
    "letter",
    "lettuce",
    "level",
    "leverage",
    "levers",
    "levitate",
    "levitator",
    "liability",
    "liable",
    "liberty",
    "librarian",
    "library",
    "licking",
    "licorice",
    "lid",
    "life",
    "lifter",
    "lifting",
    "liftoff",
    "ligament",
    "likely",
    "likeness",
    "likewise",
    "liking",
    "lilac",
    "lilly",
    "lily",
    "limb",
    "limeade",
    "limelight",
    "limes",
    "limit",
    "limping",
    "limpness",
    "line",
    "lingo",
    "linguini",
    "linguist",
    "lining",
    "linked",
    "linoleum",
    "linseed",
    "lint",
    "lion",
    "lip",
    "liquefy",
    "liqueur",
    "liquid",
    "lisp",
    "list",
    "litigate",
    "litigator",
    "litmus",
    "litter",
    "little",
    "livable",
    "lived",
    "lively",
    "liver",
    "livestock",
    "lividly",
    "living",
    "lizard",
    "lubricant",
    "lubricate",
    "lucid",
    "luckily",
    "luckiness",
    "luckless",
    "lucrative",
    "ludicrous",
    "lugged",
    "lukewarm",
    "lullaby",
    "lumber",
    "luminance",
    "luminous",
    "lumpiness",
    "lumping",
    "lumpish",
    "lunacy",
    "lunar",
    "lunchbox",
    "luncheon",
    "lunchroom",
    "lunchtime",
    "lung",
    "lurch",
    "lure",
    "luridness",
    "lurk",
    "lushly",
    "lushness",
    "luster",
    "lustfully",
    "lustily",
    "lustiness",
    "lustrous",
    "lusty",
    "luxurious",
    "luxury",
    "lying",
    "lyrically",
    "lyricism",
    "lyricist",
    "lyrics",
    "macarena",
    "macaroni",
    "macaw",
    "mace",
    "machine",
    "machinist",
    "magazine",
    "magenta",
    "maggot",
    "magical",
    "magician",
    "magma",
    "magnesium",
    "magnetic",
    "magnetism",
    "magnetize",
    "magnifier",
    "magnify",
    "magnitude",
    "magnolia",
    "mahogany",
    "maimed",
    "majestic",
    "majesty",
    "majorette",
    "majority",
    "makeover",
    "maker",
    "makeshift",
    "making",
    "malformed",
    "malt",
    "mama",
    "mammal",
    "mammary",
    "mammogram",
    "manager",
    "managing",
    "manatee",
    "mandarin",
    "mandate",
    "mandatory",
    "mandolin",
    "manger",
    "mangle",
    "mango",
    "mangy",
    "manhandle",
    "manhole",
    "manhood",
    "manhunt",
    "manicotti",
    "manicure",
    "manifesto",
    "manila",
    "mankind",
    "manlike",
    "manliness",
    "manly",
    "manmade",
    "manned",
    "mannish",
    "manor",
    "manpower",
    "mantis",
    "mantra",
    "manual",
    "many",
    "map",
    "marathon",
    "marauding",
    "marbled",
    "marbles",
    "marbling",
    "march",
    "mardi",
    "margarine",
    "margarita",
    "margin",
    "marigold",
    "marina",
    "marine",
    "marital",
    "maritime",
    "marlin",
    "marmalade",
    "maroon",
    "married",
    "marrow",
    "marry",
    "marshland",
    "marshy",
    "marsupial",
    "marvelous",
    "marxism",
    "mascot",
    "masculine",
    "mashed",
    "mashing",
    "massager",
    "masses",
    "massive",
    "mastiff",
    "matador",
    "matchbook",
    "matchbox",
    "matcher",
    "matching",
    "matchless",
    "material",
    "maternal",
    "maternity",
    "math",
    "mating",
    "matriarch",
    "matrimony",
    "matrix",
    "matron",
    "matted",
    "matter",
    "maturely",
    "maturing",
    "maturity",
    "mauve",
    "maverick",
    "maximize",
    "maximum",
    "maybe",
    "mayday",
    "mayflower",
    "moaner",
    "moaning",
    "mobile",
    "mobility",
    "mobilize",
    "mobster",
    "mocha",
    "mocker",
    "mockup",
    "modified",
    "modify",
    "modular",
    "modulator",
    "module",
    "moisten",
    "moistness",
    "moisture",
    "molar",
    "molasses",
    "mold",
    "molecular",
    "molecule",
    "molehill",
    "mollusk",
    "mom",
    "monastery",
    "monday",
    "monetary",
    "monetize",
    "moneybags",
    "moneyless",
    "moneywise",
    "mongoose",
    "mongrel",
    "monitor",
    "monkhood",
    "monogamy",
    "monogram",
    "monologue",
    "monopoly",
    "monorail",
    "monotone",
    "monotype",
    "monoxide",
    "monsieur",
    "monsoon",
    "monstrous",
    "monthly",
    "monument",
    "moocher",
    "moodiness",
    "moody",
    "mooing",
    "moonbeam",
    "mooned",
    "moonlight",
    "moonlike",
    "moonlit",
    "moonrise",
    "moonscape",
    "moonshine",
    "moonstone",
    "moonwalk",
    "mop",
    "morale",
    "morality",
    "morally",
    "morbidity",
    "morbidly",
    "morphine",
    "morphing",
    "morse",
    "mortality",
    "mortally",
    "mortician",
    "mortified",
    "mortify",
    "mortuary",
    "mosaic",
    "mossy",
    "most",
    "mothball",
    "mothproof",
    "motion",
    "motivate",
    "motivator",
    "motive",
    "motocross",
    "motor",
    "motto",
    "mountable",
    "mountain",
    "mounted",
    "mounting",
    "mourner",
    "mournful",
    "mouse",
    "mousiness",
    "moustache",
    "mousy",
    "mouth",
    "movable",
    "move",
    "movie",
    "moving",
    "mower",
    "mowing",
    "much",
    "muck",
    "mud",
    "mug",
    "mulberry",
    "mulch",
    "mule",
    "mulled",
    "mullets",
    "multiple",
    "multiply",
    "multitask",
    "multitude",
    "mumble",
    "mumbling",
    "mumbo",
    "mummified",
    "mummify",
    "mummy",
    "mumps",
    "munchkin",
    "mundane",
    "municipal",
    "muppet",
    "mural",
    "murkiness",
    "murky",
    "murmuring",
    "muscular",
    "museum",
    "mushily",
    "mushiness",
    "mushroom",
    "mushy",
    "music",
    "musket",
    "muskiness",
    "musky",
    "mustang",
    "mustard",
    "muster",
    "mustiness",
    "musty",
    "mutable",
    "mutate",
    "mutation",
    "mute",
    "mutilated",
    "mutilator",
    "mutiny",
    "mutt",
    "mutual",
    "muzzle",
    "myself",
    "myspace",
    "mystified",
    "mystify",
    "myth",
    "nacho",
    "nag",
    "nail",
    "name",
    "naming",
    "nanny",
    "nanometer",
    "nape",
    "napkin",
    "napped",
    "napping",
    "nappy",
    "narrow",
    "nastily",
    "nastiness",
    "national",
    "native",
    "nativity",
    "natural",
    "nature",
    "naturist",
    "nautical",
    "navigate",
    "navigator",
    "navy",
    "nearby",
    "nearest",
    "nearly",
    "nearness",
    "neatly",
    "neatness",
    "nebula",
    "nebulizer",
    "nectar",
    "negate",
    "negation",
    "negative",
    "neglector",
    "negligee",
    "negligent",
    "negotiate",
    "nemeses",
    "nemesis",
    "neon",
    "nephew",
    "nerd",
    "nervous",
    "nervy",
    "nest",
    "net",
    "neurology",
    "neuron",
    "neurosis",
    "neurotic",
    "neuter",
    "neutron",
    "never",
    "next",
    "nibble",
    "nickname",
    "nicotine",
    "niece",
    "nifty",
    "nimble",
    "nimbly",
    "nineteen",
    "ninetieth",
    "ninja",
    "nintendo",
    "ninth",
    "nuclear",
    "nuclei",
    "nucleus",
    "nugget",
    "nullify",
    "number",
    "numbing",
    "numbly",
    "numbness",
    "numeral",
    "numerate",
    "numerator",
    "numeric",
    "numerous",
    "nuptials",
    "nursery",
    "nursing",
    "nurture",
    "nutcase",
    "nutlike",
    "nutmeg",
    "nutrient",
    "nutshell",
    "nuttiness",
    "nutty",
    "nuzzle",
    "nylon",
    "oaf",
    "oak",
    "oasis",
    "oat",
    "obedience",
    "obedient",
    "obituary",
    "object",
    "obligate",
    "obliged",
    "oblivion",
    "oblivious",
    "oblong",
    "obnoxious",
    "oboe",
    "obscure",
    "obscurity",
    "observant",
    "observer",
    "observing",
    "obsessed",
    "obsession",
    "obsessive",
    "obsolete",
    "obstacle",
    "obstinate",
    "obstruct",
    "obtain",
    "obtrusive",
    "obtuse",
    "obvious",
    "occultist",
    "occupancy",
    "occupant",
    "occupier",
    "occupy",
    "ocean",
    "ocelot",
    "octagon",
    "octane",
    "october",
    "octopus",
    "ogle",
    "oil",
    "oink",
    "ointment",
    "okay",
    "old",
    "olive",
    "olympics",
    "omega",
    "omen",
    "ominous",
    "omission",
    "omit",
    "omnivore",
    "onboard",
    "oncoming",
    "ongoing",
    "onion",
    "online",
    "onlooker",
    "only",
    "onscreen",
    "onset",
    "onshore",
    "onslaught",
    "onstage",
    "onto",
    "onward",
    "onyx",
    "oops",
    "ooze",
    "oozy",
    "opacity",
    "opal",
    "open",
    "operable",
    "operate",
    "operating",
    "operation",
    "operative",
    "operator",
    "opium",
    "opossum",
    "opponent",
    "oppose",
    "opposing",
    "opposite",
    "oppressed",
    "oppressor",
    "opt",
    "opulently",
    "osmosis",
    "other",
    "otter",
    "ouch",
    "ought",
    "ounce",
    "outage",
    "outback",
    "outbid",
    "outboard",
    "outbound",
    "outbreak",
    "outburst",
    "outcast",
    "outclass",
    "outcome",
    "outdated",
    "outdoors",
    "outer",
    "outfield",
    "outfit",
    "outflank",
    "outgoing",
    "outgrow",
    "outhouse",
    "outing",
    "outlast",
    "outlet",
    "outline",
    "outlook",
    "outlying",
    "outmatch",
    "outmost",
    "outnumber",
    "outplayed",
    "outpost",
    "outpour",
    "output",
    "outrage",
    "outrank",
    "outreach",
    "outright",
    "outscore",
    "outsell",
    "outshine",
    "outshoot",
    "outsider",
    "outskirts",
    "outsmart",
    "outsource",
    "outspoken",
    "outtakes",
    "outthink",
    "outward",
    "outweigh",
    "outwit",
    "oval",
    "ovary",
    "oven",
    "overact",
    "overall",
    "overarch",
    "overbid",
    "overbill",
    "overbite",
    "overblown",
    "overboard",
    "overbook",
    "overbuilt",
    "overcast",
    "overcoat",
    "overcome",
    "overcook",
    "overcrowd",
    "overdraft",
    "overdrawn",
    "overdress",
    "overdrive",
    "overdue",
    "overeager",
    "overeater",
    "overexert",
    "overfed",
    "overfeed",
    "overfill",
    "overflow",
    "overfull",
    "overgrown",
    "overhand",
    "overhang",
    "overhaul",
    "overhead",
    "overhear",
    "overheat",
    "overhung",
    "overjoyed",
    "overkill",
    "overlabor",
    "overlaid",
    "overlap",
    "overlay",
    "overload",
    "overlook",
    "overlord",
    "overlying",
    "overnight",
    "overpass",
    "overpay",
    "overplant",
    "overplay",
    "overpower",
    "overprice",
    "overrate",
    "overreach",
    "overreact",
    "override",
    "overripe",
    "overrule",
    "overrun",
    "overshoot",
    "overshot",
    "oversight",
    "oversized",
    "oversleep",
    "oversold",
    "overspend",
    "overstate",
    "overstay",
    "overstep",
    "overstock",
    "overstuff",
    "oversweet",
    "overtake",
    "overthrow",
    "overtime",
    "overtly",
    "overtone",
    "overture",
    "overturn",
    "overuse",
    "overvalue",
    "overview",
    "overwrite",
    "owl",
    "oxford",
    "oxidant",
    "oxidation",
    "oxidize",
    "oxidizing",
    "oxygen",
    "oxymoron",
    "oyster",
    "ozone",
    "paced",
    "pacemaker",
    "pacific",
    "pacifier",
    "pacifism",
    "pacifist",
    "pacify",
    "padded",
    "padding",
    "paddle",
    "paddling",
    "padlock",
    "pagan",
    "pager",
    "paging",
    "pajamas",
    "palace",
    "palatable",
    "palm",
    "palpable",
    "palpitate",
    "paltry",
    "pampered",
    "pamperer",
    "pampers",
    "pamphlet",
    "panama",
    "pancake",
    "pancreas",
    "panda",
    "pandemic",
    "pang",
    "panhandle",
    "panic",
    "panning",
    "panorama",
    "panoramic",
    "panther",
    "pantomime",
    "pantry",
    "pants",
    "pantyhose",
    "paparazzi",
    "papaya",
    "paper",
    "paprika",
    "papyrus",
    "parabola",
    "parachute",
    "parade",
    "paradox",
    "paragraph",
    "parakeet",
    "paralegal",
    "paralyses",
    "paralysis",
    "paralyze",
    "paramedic",
    "parameter",
    "paramount",
    "parasail",
    "parasite",
    "parasitic",
    "parcel",
    "parched",
    "parchment",
    "pardon",
    "parish",
    "parka",
    "parking",
    "parkway",
    "parlor",
    "parmesan",
    "parole",
    "parrot",
    "parsley",
    "parsnip",
    "partake",
    "parted",
    "parting",
    "partition",
    "partly",
    "partner",
    "partridge",
    "party",
    "passable",
    "passably",
    "passage",
    "passcode",
    "passenger",
    "passerby",
    "passing",
    "passion",
    "passive",
    "passivism",
    "passover",
    "passport",
    "password",
    "pasta",
    "pasted",
    "pastel",
    "pastime",
    "pastor",
    "pastrami",
    "pasture",
    "pasty",
    "patchwork",
    "patchy",
    "paternal",
    "paternity",
    "path",
    "patience",
    "patient",
    "patio",
    "patriarch",
    "patriot",
    "patrol",
    "patronage",
    "patronize",
    "pauper",
    "pavement",
    "paver",
    "pavestone",
    "pavilion",
    "paving",
    "pawing",
    "payable",
    "payback",
    "paycheck",
    "payday",
    "payee",
    "payer",
    "paying",
    "payment",
    "payphone",
    "payroll",
    "pebble",
    "pebbly",
    "pecan",
    "pectin",
    "peculiar",
    "peddling",
    "pediatric",
    "pedicure",
    "pedigree",
    "pedometer",
    "pegboard",
    "pelican",
    "pellet",
    "pelt",
    "pelvis",
    "penalize",
    "penalty",
    "pencil",
    "pendant",
    "pending",
    "penholder",
    "penknife",
    "pennant",
    "penniless",
    "penny",
    "penpal",
    "pension",
    "pentagon",
    "pentagram",
    "pep",
    "perceive",
    "percent",
    "perch",
    "percolate",
    "perennial",
    "perfected",
    "perfectly",
    "perfume",
    "periscope",
    "perish",
    "perjurer",
    "perjury",
    "perkiness",
    "perky",
    "perm",
    "peroxide",
    "perpetual",
    "perplexed",
    "persecute",
    "persevere",
    "persuaded",
    "persuader",
    "pesky",
    "peso",
    "pessimism",
    "pessimist",
    "pester",
    "pesticide",
    "petal",
    "petite",
    "petition",
    "petri",
    "petroleum",
    "petted",
    "petticoat",
    "pettiness",
    "petty",
    "petunia",
    "phantom",
    "phobia",
    "phoenix",
    "phonebook",
    "phoney",
    "phonics",
    "phoniness",
    "phony",
    "phosphate",
    "photo",
    "phrase",
    "phrasing",
    "placard",
    "placate",
    "placidly",
    "plank",
    "planner",
    "plant",
    "plasma",
    "plaster",
    "plastic",
    "plated",
    "platform",
    "plating",
    "platinum",
    "platonic",
    "platter",
    "platypus",
    "plausible",
    "plausibly",
    "playable",
    "playback",
    "player",
    "playful",
    "playgroup",
    "playhouse",
    "playing",
    "playlist",
    "playmaker",
    "playmate",
    "playoff",
    "playpen",
    "playroom",
    "playset",
    "plaything",
    "playtime",
    "plaza",
    "pleading",
    "pleat",
    "pledge",
    "plentiful",
    "plenty",
    "plethora",
    "plexiglas",
    "pliable",
    "plod",
    "plop",
    "plot",
    "plow",
    "ploy",
    "pluck",
    "plug",
    "plunder",
    "plunging",
    "plural",
    "plus",
    "plutonium",
    "plywood",
    "poach",
    "pod",
    "poem",
    "poet",
    "pogo",
    "pointed",
    "pointer",
    "pointing",
    "pointless",
    "pointy",
    "poise",
    "poison",
    "poker",
    "poking",
    "polar",
    "police",
    "policy",
    "polio",
    "polish",
    "politely",
    "polka",
    "polo",
    "polyester",
    "polygon",
    "polygraph",
    "polymer",
    "poncho",
    "pond",
    "pony",
    "popcorn",
    "pope",
    "poplar",
    "popper",
    "poppy",
    "popsicle",
    "populace",
    "popular",
    "populate",
    "porcupine",
    "pork",
    "porous",
    "porridge",
    "portable",
    "portal",
    "portfolio",
    "porthole",
    "portion",
    "portly",
    "portside",
    "poser",
    "posh",
    "posing",
    "possible",
    "possibly",
    "possum",
    "postage",
    "postal",
    "postbox",
    "postcard",
    "posted",
    "poster",
    "posting",
    "postnasal",
    "posture",
    "postwar",
    "pouch",
    "pounce",
    "pouncing",
    "pound",
    "pouring",
    "pout",
    "powdered",
    "powdering",
    "powdery",
    "power",
    "powwow",
    "pox",
    "praising",
    "prance",
    "prancing",
    "pranker",
    "prankish",
    "prankster",
    "prayer",
    "praying",
    "preacher",
    "preaching",
    "preachy",
    "preamble",
    "precinct",
    "precise",
    "precision",
    "precook",
    "precut",
    "predator",
    "predefine",
    "predict",
    "preface",
    "prefix",
    "preflight",
    "preformed",
    "pregame",
    "pregnancy",
    "pregnant",
    "preheated",
    "prelaunch",
    "prelaw",
    "prelude",
    "premiere",
    "premises",
    "premium",
    "prenatal",
    "preoccupy",
    "preorder",
    "prepaid",
    "prepay",
    "preplan",
    "preppy",
    "preschool",
    "prescribe",
    "preseason",
    "preset",
    "preshow",
    "president",
    "presoak",
    "press",
    "presume",
    "presuming",
    "preteen",
    "pretended",
    "pretender",
    "pretense",
    "pretext",
    "pretty",
    "pretzel",
    "prevail",
    "prevalent",
    "prevent",
    "preview",
    "previous",
    "prewar",
    "prewashed",
    "prideful",
    "pried",
    "primal",
    "primarily",
    "primary",
    "primate",
    "primer",
    "primp",
    "princess",
    "print",
    "prior",
    "prism",
    "prison",
    "prissy",
    "pristine",
    "privacy",
    "private",
    "privatize",
    "prize",
    "proactive",
    "probable",
    "probably",
    "probation",
    "probe",
    "probing",
    "probiotic",
    "problem",
    "procedure",
    "process",
    "proclaim",
    "procreate",
    "procurer",
    "prodigal",
    "prodigy",
    "produce",
    "product",
    "profane",
    "profanity",
    "professed",
    "professor",
    "profile",
    "profound",
    "profusely",
    "progeny",
    "prognosis",
    "program",
    "progress",
    "projector",
    "prologue",
    "prolonged",
    "promenade",
    "prominent",
    "promoter",
    "promotion",
    "prompter",
    "promptly",
    "prone",
    "prong",
    "pronounce",
    "pronto",
    "proofing",
    "proofread",
    "proofs",
    "propeller",
    "properly",
    "property",
    "proponent",
    "proposal",
    "propose",
    "props",
    "prorate",
    "protector",
    "protegee",
    "proton",
    "prototype",
    "protozoan",
    "protract",
    "protrude",
    "proud",
    "provable",
    "proved",
    "proven",
    "provided",
    "provider",
    "providing",
    "province",
    "proving",
    "provoke",
    "provoking",
    "provolone",
    "prowess",
    "prowler",
    "prowling",
    "proximity",
    "proxy",
    "prozac",
    "prude",
    "prudishly",
    "prune",
    "pruning",
    "pry",
    "psychic",
    "public",
    "publisher",
    "pucker",
    "pueblo",
    "pug",
    "pull",
    "pulmonary",
    "pulp",
    "pulsate",
    "pulse",
    "pulverize",
    "puma",
    "pumice",
    "pummel",
    "punch",
    "punctual",
    "punctuate",
    "punctured",
    "pungent",
    "punisher",
    "punk",
    "pupil",
    "puppet",
    "puppy",
    "purchase",
    "pureblood",
    "purebred",
    "purely",
    "pureness",
    "purgatory",
    "purge",
    "purging",
    "purifier",
    "purify",
    "purist",
    "puritan",
    "purity",
    "purple",
    "purplish",
    "purposely",
    "purr",
    "purse",
    "pursuable",
    "pursuant",
    "pursuit",
    "purveyor",
    "pushcart",
    "pushchair",
    "pusher",
    "pushiness",
    "pushing",
    "pushover",
    "pushpin",
    "pushup",
    "pushy",
    "putdown",
    "putt",
    "puzzle",
    "puzzling",
    "pyramid",
    "pyromania",
    "python",
    "quack",
    "quadrant",
    "quail",
    "quaintly",
    "quake",
    "quaking",
    "qualified",
    "qualifier",
    "qualify",
    "quality",
    "qualm",
    "quantum",
    "quarrel",
    "quarry",
    "quartered",
    "quarterly",
    "quarters",
    "quartet",
    "quench",
    "query",
    "quicken",
    "quickly",
    "quickness",
    "quicksand",
    "quickstep",
    "quiet",
    "quill",
    "quilt",
    "quintet",
    "quintuple",
    "quirk",
    "quit",
    "quiver",
    "quizzical",
    "quotable",
    "quotation",
    "quote",
    "rabid",
    "race",
    "racing",
    "racism",
    "rack",
    "racoon",
    "radar",
    "radial",
    "radiance",
    "radiantly",
    "radiated",
    "radiation",
    "radiator",
    "radio",
    "radish",
    "raffle",
    "raft",
    "rage",
    "ragged",
    "raging",
    "ragweed",
    "raider",
    "railcar",
    "railing",
    "railroad",
    "railway",
    "raisin",
    "rake",
    "raking",
    "rally",
    "ramble",
    "rambling",
    "ramp",
    "ramrod",
    "ranch",
    "rancidity",
    "random",
    "ranged",
    "ranger",
    "ranging",
    "ranked",
    "ranking",
    "ransack",
    "ranting",
    "rants",
    "rare",
    "rarity",
    "rascal",
    "rash",
    "rasping",
    "ravage",
    "raven",
    "ravine",
    "raving",
    "ravioli",
    "ravishing",
    "reabsorb",
    "reach",
    "reacquire",
    "reaction",
    "reactive",
    "reactor",
    "reaffirm",
    "ream",
    "reanalyze",
    "reappear",
    "reapply",
    "reappoint",
    "reapprove",
    "rearrange",
    "rearview",
    "reason",
    "reassign",
    "reassure",
    "reattach",
    "reawake",
    "rebalance",
    "rebate",
    "rebel",
    "rebirth",
    "reboot",
    "reborn",
    "rebound",
    "rebuff",
    "rebuild",
    "rebuilt",
    "reburial",
    "rebuttal",
    "recall",
    "recant",
    "recapture",
    "recast",
    "recede",
    "recent",
    "recess",
    "recharger",
    "recipient",
    "recital",
    "recite",
    "reckless",
    "reclaim",
    "recliner",
    "reclining",
    "recluse",
    "reclusive",
    "recognize",
    "recoil",
    "recollect",
    "recolor",
    "reconcile",
    "reconfirm",
    "reconvene",
    "recopy",
    "record",
    "recount",
    "recoup",
    "recovery",
    "recreate",
    "rectal",
    "rectangle",
    "rectified",
    "rectify",
    "recycled",
    "recycler",
    "recycling",
    "reemerge",
    "reenact",
    "reenter",
    "reentry",
    "reexamine",
    "referable",
    "referee",
    "reference",
    "refill",
    "refinance",
    "refined",
    "refinery",
    "refining",
    "refinish",
    "reflected",
    "reflector",
    "reflex",
    "reflux",
    "refocus",
    "refold",
    "reforest",
    "reformat",
    "reformed",
    "reformer",
    "reformist",
    "refract",
    "refrain",
    "refreeze",
    "refresh",
    "refried",
    "refueling",
    "refund",
    "refurbish",
    "refurnish",
    "refusal",
    "refuse",
    "refusing",
    "refutable",
    "refute",
    "regain",
    "regalia",
    "regally",
    "reggae",
    "regime",
    "region",
    "register",
    "registrar",
    "registry",
    "regress",
    "regretful",
    "regroup",
    "regular",
    "regulate",
    "regulator",
    "rehab",
    "reheat",
    "rehire",
    "rehydrate",
    "reimburse",
    "reissue",
    "reiterate",
    "rejoice",
    "rejoicing",
    "rejoin",
    "rekindle",
    "relapse",
    "relapsing",
    "relatable",
    "related",
    "relation",
    "relative",
    "relax",
    "relay",
    "relearn",
    "release",
    "relenting",
    "reliable",
    "reliably",
    "reliance",
    "reliant",
    "relic",
    "relieve",
    "relieving",
    "relight",
    "relish",
    "relive",
    "reload",
    "relocate",
    "relock",
    "reluctant",
    "rely",
    "remake",
    "remark",
    "remarry",
    "rematch",
    "remedial",
    "remedy",
    "remember",
    "reminder",
    "remindful",
    "remission",
    "remix",
    "remnant",
    "remodeler",
    "remold",
    "remorse",
    "remote",
    "removable",
    "removal",
    "removed",
    "remover",
    "removing",
    "rename",
    "renderer",
    "rendering",
    "rendition",
    "renegade",
    "renewable",
    "renewably",
    "renewal",
    "renewed",
    "renounce",
    "renovate",
    "renovator",
    "rentable",
    "rental",
    "rented",
    "renter",
    "reoccupy",
    "reoccur",
    "reopen",
    "reorder",
    "repackage",
    "repacking",
    "repaint",
    "repair",
    "repave",
    "repaying",
    "repayment",
    "repeal",
    "repeated",
    "repeater",
    "repent",
    "rephrase",
    "replace",
    "replay",
    "replica",
    "reply",
    "reporter",
    "repose",
    "repossess",
    "repost",
    "repressed",
    "reprimand",
    "reprint",
    "reprise",
    "reproach",
    "reprocess",
    "reproduce",
    "reprogram",
    "reps",
    "reptile",
    "reptilian",
    "repugnant",
    "repulsion",
    "repulsive",
    "repurpose",
    "reputable",
    "reputably",
    "request",
    "require",
    "requisite",
    "reroute",
    "rerun",
    "resale",
    "resample",
    "rescuer",
    "reseal",
    "research",
    "reselect",
    "reseller",
    "resemble",
    "resend",
    "resent",
    "reset",
    "reshape",
    "reshoot",
    "reshuffle",
    "residence",
    "residency",
    "resident",
    "residual",
    "residue",
    "resigned",
    "resilient",
    "resistant",
    "resisting",
    "resize",
    "resolute",
    "resolved",
    "resonant",
    "resonate",
    "resort",
    "resource",
    "respect",
    "resubmit",
    "result",
    "resume",
    "resupply",
    "resurface",
    "resurrect",
    "retail",
    "retainer",
    "retaining",
    "retake",
    "retaliate",
    "retention",
    "rethink",
    "retinal",
    "retired",
    "retiree",
    "retiring",
    "retold",
    "retool",
    "retorted",
    "retouch",
    "retrace",
    "retract",
    "retrain",
    "retread",
    "retreat",
    "retrial",
    "retrieval",
    "retriever",
    "retry",
    "return",
    "retying",
    "retype",
    "reunion",
    "reunite",
    "reusable",
    "reuse",
    "reveal",
    "reveler",
    "revenge",
    "revenue",
    "reverb",
    "revered",
    "reverence",
    "reverend",
    "reversal",
    "reverse",
    "reversing",
    "reversion",
    "revert",
    "revisable",
    "revise",
    "revision",
    "revisit",
    "revivable",
    "revival",
    "reviver",
    "reviving",
    "revocable",
    "revoke",
    "revolt",
    "revolver",
    "revolving",
    "reward",
    "rewash",
    "rewind",
    "rewire",
    "reword",
    "rework",
    "rewrap",
    "rewrite",
    "rhyme",
    "ribbon",
    "ribcage",
    "rice",
    "riches",
    "richly",
    "richness",
    "rickety",
    "ricotta",
    "riddance",
    "ridden",
    "ride",
    "riding",
    "rifling",
    "rift",
    "rigging",
    "rigid",
    "rigor",
    "rimless",
    "rimmed",
    "rind",
    "rink",
    "rinse",
    "rinsing",
    "riot",
    "ripcord",
    "ripeness",
    "ripening",
    "ripping",
    "ripple",
    "rippling",
    "riptide",
    "rise",
    "rising",
    "risk",
    "risotto",
    "ritalin",
    "ritzy",
    "rival",
    "riverbank",
    "riverbed",
    "riverboat",
    "riverside",
    "riveter",
    "riveting",
    "roamer",
    "roaming",
    "roast",
    "robbing",
    "robe",
    "robin",
    "robotics",
    "robust",
    "rockband",
    "rocker",
    "rocket",
    "rockfish",
    "rockiness",
    "rocking",
    "rocklike",
    "rockslide",
    "rockstar",
    "rocky",
    "rogue",
    "roman",
    "romp",
    "rope",
    "roping",
    "roster",
    "rosy",
    "rotten",
    "rotting",
    "rotunda",
    "roulette",
    "rounding",
    "roundish",
    "roundness",
    "roundup",
    "roundworm",
    "routine",
    "routing",
    "rover",
    "roving",
    "royal",
    "rubbed",
    "rubber",
    "rubbing",
    "rubble",
    "rubdown",
    "ruby",
    "ruckus",
    "rudder",
    "rug",
    "ruined",
    "rule",
    "rumble",
    "rumbling",
    "rummage",
    "rumor",
    "runaround",
    "rundown",
    "runner",
    "running",
    "runny",
    "runt",
    "runway",
    "rupture",
    "rural",
    "ruse",
    "rush",
    "rust",
    "rut",
    "sabbath",
    "sabotage",
    "sacrament",
    "sacred",
    "sacrifice",
    "sadden",
    "saddlebag",
    "saddled",
    "saddling",
    "sadly",
    "sadness",
    "safari",
    "safeguard",
    "safehouse",
    "safely",
    "safeness",
    "saffron",
    "saga",
    "sage",
    "sagging",
    "saggy",
    "said",
    "saint",
    "sake",
    "salad",
    "salami",
    "salaried",
    "salary",
    "saline",
    "salon",
    "saloon",
    "salsa",
    "salt",
    "salutary",
    "salute",
    "salvage",
    "salvaging",
    "salvation",
    "same",
    "sample",
    "sampling",
    "sanction",
    "sanctity",
    "sanctuary",
    "sandal",
    "sandbag",
    "sandbank",
    "sandbar",
    "sandblast",
    "sandbox",
    "sanded",
    "sandfish",
    "sanding",
    "sandlot",
    "sandpaper",
    "sandpit",
    "sandstone",
    "sandstorm",
    "sandworm",
    "sandy",
    "sanitary",
    "sanitizer",
    "sank",
    "santa",
    "sapling",
    "sappiness",
    "sappy",
    "sarcasm",
    "sarcastic",
    "sardine",
    "sash",
    "sasquatch",
    "sassy",
    "satchel",
    "satiable",
    "satin",
    "satirical",
    "satisfied",
    "satisfy",
    "saturate",
    "saturday",
    "sauciness",
    "saucy",
    "sauna",
    "savage",
    "savanna",
    "saved",
    "savings",
    "savior",
    "savor",
    "saxophone",
    "say",
    "scabbed",
    "scabby",
    "scalded",
    "scalding",
    "scale",
    "scaling",
    "scallion",
    "scallop",
    "scalping",
    "scam",
    "scandal",
    "scanner",
    "scanning",
    "scant",
    "scapegoat",
    "scarce",
    "scarcity",
    "scarecrow",
    "scared",
    "scarf",
    "scarily",
    "scariness",
    "scarring",
    "scary",
    "scavenger",
    "scenic",
    "schedule",
    "schematic",
    "scheme",
    "scheming",
    "schilling",
    "schnapps",
    "scholar",
    "science",
    "scientist",
    "scion",
    "scoff",
    "scolding",
    "scone",
    "scoop",
    "scooter",
    "scope",
    "scorch",
    "scorebook",
    "scorecard",
    "scored",
    "scoreless",
    "scorer",
    "scoring",
    "scorn",
    "scorpion",
    "scotch",
    "scoundrel",
    "scoured",
    "scouring",
    "scouting",
    "scouts",
    "scowling",
    "scrabble",
    "scraggly",
    "scrambled",
    "scrambler",
    "scrap",
    "scratch",
    "scrawny",
    "screen",
    "scribble",
    "scribe",
    "scribing",
    "scrimmage",
    "script",
    "scroll",
    "scrooge",
    "scrounger",
    "scrubbed",
    "scrubber",
    "scruffy",
    "scrunch",
    "scrutiny",
    "scuba",
    "scuff",
    "sculptor",
    "sculpture",
    "scurvy",
    "scuttle",
    "secluded",
    "secluding",
    "seclusion",
    "second",
    "secrecy",
    "secret",
    "sectional",
    "sector",
    "secular",
    "securely",
    "security",
    "sedan",
    "sedate",
    "sedation",
    "sedative",
    "sediment",
    "seduce",
    "seducing",
    "segment",
    "seismic",
    "seizing",
    "seldom",
    "selected",
    "selection",
    "selective",
    "selector",
    "self",
    "seltzer",
    "semantic",
    "semester",
    "semicolon",
    "semifinal",
    "seminar",
    "semisoft",
    "semisweet",
    "senate",
    "senator",
    "send",
    "senior",
    "senorita",
    "sensation",
    "sensitive",
    "sensitize",
    "sensually",
    "sensuous",
    "sepia",
    "september",
    "septic",
    "septum",
    "sequel",
    "sequence",
    "sequester",
    "series",
    "sermon",
    "serotonin",
    "serpent",
    "serrated",
    "serve",
    "service",
    "serving",
    "sesame",
    "sessions",
    "setback",
    "setting",
    "settle",
    "settling",
    "setup",
    "sevenfold",
    "seventeen",
    "seventh",
    "seventy",
    "severity",
    "shabby",
    "shack",
    "shaded",
    "shadily",
    "shadiness",
    "shading",
    "shadow",
    "shady",
    "shaft",
    "shakable",
    "shakily",
    "shakiness",
    "shaking",
    "shaky",
    "shale",
    "shallot",
    "shallow",
    "shame",
    "shampoo",
    "shamrock",
    "shank",
    "shanty",
    "shape",
    "shaping",
    "share",
    "sharpener",
    "sharper",
    "sharpie",
    "sharply",
    "sharpness",
    "shawl",
    "sheath",
    "shed",
    "sheep",
    "sheet",
    "shelf",
    "shell",
    "shelter",
    "shelve",
    "shelving",
    "sherry",
    "shield",
    "shifter",
    "shifting",
    "shiftless",
    "shifty",
    "shimmer",
    "shimmy",
    "shindig",
    "shine",
    "shingle",
    "shininess",
    "shining",
    "shiny",
    "ship",
    "shirt",
    "shivering",
    "shock",
    "shone",
    "shoplift",
    "shopper",
    "shopping",
    "shoptalk",
    "shore",
    "shortage",
    "shortcake",
    "shortcut",
    "shorten",
    "shorter",
    "shorthand",
    "shortlist",
    "shortly",
    "shortness",
    "shorts",
    "shortwave",
    "shorty",
    "shout",
    "shove",
    "showbiz",
    "showcase",
    "showdown",
    "shower",
    "showgirl",
    "showing",
    "showman",
    "shown",
    "showoff",
    "showpiece",
    "showplace",
    "showroom",
    "showy",
    "shrank",
    "shrapnel",
    "shredder",
    "shredding",
    "shrewdly",
    "shriek",
    "shrill",
    "shrimp",
    "shrine",
    "shrink",
    "shrivel",
    "shrouded",
    "shrubbery",
    "shrubs",
    "shrug",
    "shrunk",
    "shucking",
    "shudder",
    "shuffle",
    "shuffling",
    "shun",
    "shush",
    "shut",
    "shy",
    "siamese",
    "siberian",
    "sibling",
    "siding",
    "sierra",
    "siesta",
    "sift",
    "sighing",
    "silenced",
    "silencer",
    "silent",
    "silica",
    "silicon",
    "silk",
    "silliness",
    "silly",
    "silo",
    "silt",
    "silver",
    "similarly",
    "simile",
    "simmering",
    "simple",
    "simplify",
    "simply",
    "sincere",
    "sincerity",
    "singer",
    "singing",
    "single",
    "singular",
    "sinister",
    "sinless",
    "sinner",
    "sinuous",
    "sip",
    "siren",
    "sister",
    "sitcom",
    "sitter",
    "sitting",
    "situated",
    "situation",
    "sixfold",
    "sixteen",
    "sixth",
    "sixties",
    "sixtieth",
    "sixtyfold",
    "sizable",
    "sizably",
    "size",
    "sizing",
    "sizzle",
    "sizzling",
    "skater",
    "skating",
    "skedaddle",
    "skeletal",
    "skeleton",
    "skeptic",
    "sketch",
    "skewed",
    "skewer",
    "skid",
    "skied",
    "skier",
    "skies",
    "skiing",
    "skilled",
    "skillet",
    "skillful",
    "skimmed",
    "skimmer",
    "skimming",
    "skimpily",
    "skincare",
    "skinhead",
    "skinless",
    "skinning",
    "skinny",
    "skintight",
    "skipper",
    "skipping",
    "skirmish",
    "skirt",
    "skittle",
    "skydiver",
    "skylight",
    "skyline",
    "skype",
    "skyrocket",
    "skyward",
    "slab",
    "slacked",
    "slacker",
    "slacking",
    "slackness",
    "slacks",
    "slain",
    "slam",
    "slander",
    "slang",
    "slapping",
    "slapstick",
    "slashed",
    "slashing",
    "slate",
    "slather",
    "slaw",
    "sled",
    "sleek",
    "sleep",
    "sleet",
    "sleeve",
    "slept",
    "sliceable",
    "sliced",
    "slicer",
    "slicing",
    "slick",
    "slider",
    "slideshow",
    "sliding",
    "slighted",
    "slighting",
    "slightly",
    "slimness",
    "slimy",
    "slinging",
    "slingshot",
    "slinky",
    "slip",
    "slit",
    "sliver",
    "slobbery",
    "slogan",
    "sloped",
    "sloping",
    "sloppily",
    "sloppy",
    "slot",
    "slouching",
    "slouchy",
    "sludge",
    "slug",
    "slum",
    "slurp",
    "slush",
    "sly",
    "small",
    "smartly",
    "smartness",
    "smasher",
    "smashing",
    "smashup",
    "smell",
    "smelting",
    "smile",
    "smilingly",
    "smirk",
    "smite",
    "smith",
    "smitten",
    "smock",
    "smog",
    "smoked",
    "smokeless",
    "smokiness",
    "smoking",
    "smoky",
    "smolder",
    "smooth",
    "smother",
    "smudge",
    "smudgy",
    "smuggler",
    "smuggling",
    "smugly",
    "smugness",
    "snack",
    "snagged",
    "snaking",
    "snap",
    "snare",
    "snarl",
    "snazzy",
    "sneak",
    "sneer",
    "sneeze",
    "sneezing",
    "snide",
    "sniff",
    "snippet",
    "snipping",
    "snitch",
    "snooper",
    "snooze",
    "snore",
    "snoring",
    "snorkel",
    "snort",
    "snout",
    "snowbird",
    "snowboard",
    "snowbound",
    "snowcap",
    "snowdrift",
    "snowdrop",
    "snowfall",
    "snowfield",
    "snowflake",
    "snowiness",
    "snowless",
    "snowman",
    "snowplow",
    "snowshoe",
    "snowstorm",
    "snowsuit",
    "snowy",
    "snub",
    "snuff",
    "snuggle",
    "snugly",
    "snugness",
    "speak",
    "spearfish",
    "spearhead",
    "spearman",
    "spearmint",
    "species",
    "specimen",
    "specked",
    "speckled",
    "specks",
    "spectacle",
    "spectator",
    "spectrum",
    "speculate",
    "speech",
    "speed",
    "spellbind",
    "speller",
    "spelling",
    "spendable",
    "spender",
    "spending",
    "spent",
    "spew",
    "sphere",
    "spherical",
    "sphinx",
    "spider",
    "spied",
    "spiffy",
    "spill",
    "spilt",
    "spinach",
    "spinal",
    "spindle",
    "spinner",
    "spinning",
    "spinout",
    "spinster",
    "spiny",
    "spiral",
    "spirited",
    "spiritism",
    "spirits",
    "spiritual",
    "splashed",
    "splashing",
    "splashy",
    "splatter",
    "spleen",
    "splendid",
    "splendor",
    "splice",
    "splicing",
    "splinter",
    "splotchy",
    "splurge",
    "spoilage",
    "spoiled",
    "spoiler",
    "spoiling",
    "spoils",
    "spoken",
    "spokesman",
    "sponge",
    "spongy",
    "sponsor",
    "spoof",
    "spookily",
    "spooky",
    "spool",
    "spoon",
    "spore",
    "sporting",
    "sports",
    "sporty",
    "spotless",
    "spotlight",
    "spotted",
    "spotter",
    "spotting",
    "spotty",
    "spousal",
    "spouse",
    "spout",
    "sprain",
    "sprang",
    "sprawl",
    "spray",
    "spree",
    "sprig",
    "spring",
    "sprinkled",
    "sprinkler",
    "sprint",
    "sprite",
    "sprout",
    "spruce",
    "sprung",
    "spry",
    "spud",
    "spur",
    "sputter",
    "spyglass",
    "squabble",
    "squad",
    "squall",
    "squander",
    "squash",
    "squatted",
    "squatter",
    "squatting",
    "squeak",
    "squealer",
    "squealing",
    "squeamish",
    "squeegee",
    "squeeze",
    "squeezing",
    "squid",
    "squiggle",
    "squiggly",
    "squint",
    "squire",
    "squirt",
    "squishier",
    "squishy",
    "stability",
    "stabilize",
    "stable",
    "stack",
    "stadium",
    "staff",
    "stage",
    "staging",
    "stagnant",
    "stagnate",
    "stainable",
    "stained",
    "staining",
    "stainless",
    "stalemate",
    "staleness",
    "stalling",
    "stallion",
    "stamina",
    "stammer",
    "stamp",
    "stand",
    "stank",
    "staple",
    "stapling",
    "starboard",
    "starch",
    "stardom",
    "stardust",
    "starfish",
    "stargazer",
    "staring",
    "stark",
    "starless",
    "starlet",
    "starlight",
    "starlit",
    "starring",
    "starry",
    "starship",
    "starter",
    "starting",
    "startle",
    "startling",
    "startup",
    "starved",
    "starving",
    "stash",
    "state",
    "static",
    "statistic",
    "statue",
    "stature",
    "status",
    "statute",
    "statutory",
    "staunch",
    "stays",
    "steadfast",
    "steadier",
    "steadily",
    "steadying",
    "steam",
    "steed",
    "steep",
    "steerable",
    "steering",
    "steersman",
    "stegosaur",
    "stellar",
    "stem",
    "stench",
    "stencil",
    "step",
    "stereo",
    "sterile",
    "sterility",
    "sterilize",
    "sterling",
    "sternness",
    "sternum",
    "stew",
    "stick",
    "stiffen",
    "stiffly",
    "stiffness",
    "stifle",
    "stifling",
    "stillness",
    "stilt",
    "stimulant",
    "stimulate",
    "stimuli",
    "stimulus",
    "stinger",
    "stingily",
    "stinging",
    "stingray",
    "stingy",
    "stinking",
    "stinky",
    "stipend",
    "stipulate",
    "stir",
    "stitch",
    "stock",
    "stoic",
    "stoke",
    "stole",
    "stomp",
    "stonewall",
    "stoneware",
    "stonework",
    "stoning",
    "stony",
    "stood",
    "stooge",
    "stool",
    "stoop",
    "stoplight",
    "stoppable",
    "stoppage",
    "stopped",
    "stopper",
    "stopping",
    "stopwatch",
    "storable",
    "storage",
    "storeroom",
    "storewide",
    "storm",
    "stout",
    "stove",
    "stowaway",
    "stowing",
    "straddle",
    "straggler",
    "strained",
    "strainer",
    "straining",
    "strangely",
    "stranger",
    "strangle",
    "strategic",
    "strategy",
    "stratus",
    "straw",
    "stray",
    "streak",
    "stream",
    "street",
    "strength",
    "strenuous",
    "strep",
    "stress",
    "stretch",
    "strewn",
    "stricken",
    "strict",
    "stride",
    "strife",
    "strike",
    "striking",
    "strive",
    "striving",
    "strobe",
    "strode",
    "stroller",
    "strongbox",
    "strongly",
    "strongman",
    "struck",
    "structure",
    "strudel",
    "struggle",
    "strum",
    "strung",
    "strut",
    "stubbed",
    "stubble",
    "stubbly",
    "stubborn",
    "stucco",
    "stuck",
    "student",
    "studied",
    "studio",
    "study",
    "stuffed",
    "stuffing",
    "stuffy",
    "stumble",
    "stumbling",
    "stump",
    "stung",
    "stunned",
    "stunner",
    "stunning",
    "stunt",
    "stupor",
    "sturdily",
    "sturdy",
    "styling",
    "stylishly",
    "stylist",
    "stylized",
    "stylus",
    "suave",
    "subarctic",
    "subatomic",
    "subdivide",
    "subdued",
    "subduing",
    "subfloor",
    "subgroup",
    "subheader",
    "subject",
    "sublease",
    "sublet",
    "sublevel",
    "sublime",
    "submarine",
    "submerge",
    "submersed",
    "submitter",
    "subpanel",
    "subpar",
    "subplot",
    "subprime",
    "subscribe",
    "subscript",
    "subsector",
    "subside",
    "subsiding",
    "subsidize",
    "subsidy",
    "subsoil",
    "subsonic",
    "substance",
    "subsystem",
    "subtext",
    "subtitle",
    "subtly",
    "subtotal",
    "subtract",
    "subtype",
    "suburb",
    "subway",
    "subwoofer",
    "subzero",
    "succulent",
    "such",
    "suction",
    "sudden",
    "sudoku",
    "suds",
    "sufferer",
    "suffering",
    "suffice",
    "suffix",
    "suffocate",
    "suffrage",
    "sugar",
    "suggest",
    "suing",
    "suitable",
    "suitably",
    "suitcase",
    "suitor",
    "sulfate",
    "sulfide",
    "sulfite",
    "sulfur",
    "sulk",
    "sullen",
    "sulphate",
    "sulphuric",
    "sultry",
    "superbowl",
    "superglue",
    "superhero",
    "superior",
    "superjet",
    "superman",
    "supermom",
    "supernova",
    "supervise",
    "supper",
    "supplier",
    "supply",
    "support",
    "supremacy",
    "supreme",
    "surcharge",
    "surely",
    "sureness",
    "surface",
    "surfacing",
    "surfboard",
    "surfer",
    "surgery",
    "surgical",
    "surging",
    "surname",
    "surpass",
    "surplus",
    "surprise",
    "surreal",
    "surrender",
    "surrogate",
    "surround",
    "survey",
    "survival",
    "survive",
    "surviving",
    "survivor",
    "sushi",
    "suspect",
    "suspend",
    "suspense",
    "sustained",
    "sustainer",
    "swab",
    "swaddling",
    "swagger",
    "swampland",
    "swan",
    "swapping",
    "swarm",
    "sway",
    "swear",
    "sweat",
    "sweep",
    "swell",
    "swept",
    "swerve",
    "swifter",
    "swiftly",
    "swiftness",
    "swimmable",
    "swimmer",
    "swimming",
    "swimsuit",
    "swimwear",
    "swinger",
    "swinging",
    "swipe",
    "swirl",
    "switch",
    "swivel",
    "swizzle",
    "swooned",
    "swoop",
    "swoosh",
    "swore",
    "sworn",
    "swung",
    "sycamore",
    "sympathy",
    "symphonic",
    "symphony",
    "symptom",
    "synapse",
    "syndrome",
    "synergy",
    "synopses",
    "synopsis",
    "synthesis",
    "synthetic",
    "syrup",
    "system",
    "t-shirt",
    "tabasco",
    "tabby",
    "tableful",
    "tables",
    "tablet",
    "tableware",
    "tabloid",
    "tackiness",
    "tacking",
    "tackle",
    "tackling",
    "tacky",
    "taco",
    "tactful",
    "tactical",
    "tactics",
    "tactile",
    "tactless",
    "tadpole",
    "taekwondo",
    "tag",
    "tainted",
    "take",
    "taking",
    "talcum",
    "talisman",
    "tall",
    "talon",
    "tamale",
    "tameness",
    "tamer",
    "tamper",
    "tank",
    "tanned",
    "tannery",
    "tanning",
    "tantrum",
    "tapeless",
    "tapered",
    "tapering",
    "tapestry",
    "tapioca",
    "tapping",
    "taps",
    "tarantula",
    "target",
    "tarmac",
    "tarnish",
    "tarot",
    "tartar",
    "tartly",
    "tartness",
    "task",
    "tassel",
    "taste",
    "tastiness",
    "tasting",
    "tasty",
    "tattered",
    "tattle",
    "tattling",
    "tattoo",
    "taunt",
    "tavern",
    "thank",
    "that",
    "thaw",
    "theater",
    "theatrics",
    "thee",
    "theft",
    "theme",
    "theology",
    "theorize",
    "thermal",
    "thermos",
    "thesaurus",
    "these",
    "thesis",
    "thespian",
    "thicken",
    "thicket",
    "thickness",
    "thieving",
    "thievish",
    "thigh",
    "thimble",
    "thing",
    "think",
    "thinly",
    "thinner",
    "thinness",
    "thinning",
    "thirstily",
    "thirsting",
    "thirsty",
    "thirteen",
    "thirty",
    "thong",
    "thorn",
    "those",
    "thousand",
    "thrash",
    "thread",
    "threaten",
    "threefold",
    "thrift",
    "thrill",
    "thrive",
    "thriving",
    "throat",
    "throbbing",
    "throng",
    "throttle",
    "throwaway",
    "throwback",
    "thrower",
    "throwing",
    "thud",
    "thumb",
    "thumping",
    "thursday",
    "thus",
    "thwarting",
    "thyself",
    "tiara",
    "tibia",
    "tidal",
    "tidbit",
    "tidiness",
    "tidings",
    "tidy",
    "tiger",
    "tighten",
    "tightly",
    "tightness",
    "tightrope",
    "tightwad",
    "tigress",
    "tile",
    "tiling",
    "till",
    "tilt",
    "timid",
    "timing",
    "timothy",
    "tinderbox",
    "tinfoil",
    "tingle",
    "tingling",
    "tingly",
    "tinker",
    "tinkling",
    "tinsel",
    "tinsmith",
    "tint",
    "tinwork",
    "tiny",
    "tipoff",
    "tipped",
    "tipper",
    "tipping",
    "tiptoeing",
    "tiptop",
    "tiring",
    "tissue",
    "trace",
    "tracing",
    "track",
    "traction",
    "tractor",
    "trade",
    "trading",
    "tradition",
    "traffic",
    "tragedy",
    "trailing",
    "trailside",
    "train",
    "traitor",
    "trance",
    "tranquil",
    "transfer",
    "transform",
    "translate",
    "transpire",
    "transport",
    "transpose",
    "trapdoor",
    "trapeze",
    "trapezoid",
    "trapped",
    "trapper",
    "trapping",
    "traps",
    "trash",
    "travel",
    "traverse",
    "travesty",
    "tray",
    "treachery",
    "treading",
    "treadmill",
    "treason",
    "treat",
    "treble",
    "tree",
    "trekker",
    "tremble",
    "trembling",
    "tremor",
    "trench",
    "trend",
    "trespass",
    "triage",
    "trial",
    "triangle",
    "tribesman",
    "tribunal",
    "tribune",
    "tributary",
    "tribute",
    "triceps",
    "trickery",
    "trickily",
    "tricking",
    "trickle",
    "trickster",
    "tricky",
    "tricolor",
    "tricycle",
    "trident",
    "tried",
    "trifle",
    "trifocals",
    "trillion",
    "trilogy",
    "trimester",
    "trimmer",
    "trimming",
    "trimness",
    "trinity",
    "trio",
    "tripod",
    "tripping",
    "triumph",
    "trivial",
    "trodden",
    "trolling",
    "trombone",
    "trophy",
    "tropical",
    "tropics",
    "trouble",
    "troubling",
    "trough",
    "trousers",
    "trout",
    "trowel",
    "truce",
    "truck",
    "truffle",
    "trump",
    "trunks",
    "trustable",
    "trustee",
    "trustful",
    "trusting",
    "trustless",
    "truth",
    "try",
    "tubby",
    "tubeless",
    "tubular",
    "tucking",
    "tuesday",
    "tug",
    "tuition",
    "tulip",
    "tumble",
    "tumbling",
    "tummy",
    "turban",
    "turbine",
    "turbofan",
    "turbojet",
    "turbulent",
    "turf",
    "turkey",
    "turmoil",
    "turret",
    "turtle",
    "tusk",
    "tutor",
    "tutu",
    "tux",
    "tweak",
    "tweed",
    "tweet",
    "tweezers",
    "twelve",
    "twentieth",
    "twenty",
    "twerp",
    "twice",
    "twiddle",
    "twiddling",
    "twig",
    "twilight",
    "twine",
    "twins",
    "twirl",
    "twistable",
    "twisted",
    "twister",
    "twisting",
    "twisty",
    "twitch",
    "twitter",
    "tycoon",
    "tying",
    "tyke",
    "udder",
    "ultimate",
    "ultimatum",
    "ultra",
    "umbilical",
    "umbrella",
    "umpire",
    "unabashed",
    "unable",
    "unadorned",
    "unadvised",
    "unafraid",
    "unaired",
    "unaligned",
    "unaltered",
    "unarmored",
    "unashamed",
    "unaudited",
    "unawake",
    "unaware",
    "unbaked",
    "unbalance",
    "unbeaten",
    "unbend",
    "unbent",
    "unbiased",
    "unbitten",
    "unblended",
    "unblessed",
    "unblock",
    "unbolted",
    "unbounded",
    "unboxed",
    "unbraided",
    "unbridle",
    "unbroken",
    "unbuckled",
    "unbundle",
    "unburned",
    "unbutton",
    "uncanny",
    "uncapped",
    "uncaring",
    "uncertain",
    "unchain",
    "unchanged",
    "uncharted",
    "uncheck",
    "uncivil",
    "unclad",
    "unclaimed",
    "unclamped",
    "unclasp",
    "uncle",
    "unclip",
    "uncloak",
    "unclog",
    "unclothed",
    "uncoated",
    "uncoiled",
    "uncolored",
    "uncombed",
    "uncommon",
    "uncooked",
    "uncork",
    "uncorrupt",
    "uncounted",
    "uncouple",
    "uncouth",
    "uncover",
    "uncross",
    "uncrown",
    "uncrushed",
    "uncured",
    "uncurious",
    "uncurled",
    "uncut",
    "undamaged",
    "undated",
    "undaunted",
    "undead",
    "undecided",
    "undefined",
    "underage",
    "underarm",
    "undercoat",
    "undercook",
    "undercut",
    "underdog",
    "underdone",
    "underfed",
    "underfeed",
    "underfoot",
    "undergo",
    "undergrad",
    "underhand",
    "underline",
    "underling",
    "undermine",
    "undermost",
    "underpaid",
    "underpass",
    "underpay",
    "underrate",
    "undertake",
    "undertone",
    "undertook",
    "undertow",
    "underuse",
    "underwear",
    "underwent",
    "underwire",
    "undesired",
    "undiluted",
    "undivided",
    "undocked",
    "undoing",
    "undone",
    "undrafted",
    "undress",
    "undrilled",
    "undusted",
    "undying",
    "unearned",
    "unearth",
    "unease",
    "uneasily",
    "uneasy",
    "uneatable",
    "uneaten",
    "unedited",
    "unelected",
    "unending",
    "unengaged",
    "unenvied",
    "unequal",
    "unethical",
    "uneven",
    "unexpired",
    "unexposed",
    "unfailing",
    "unfair",
    "unfasten",
    "unfazed",
    "unfeeling",
    "unfiled",
    "unfilled",
    "unfitted",
    "unfitting",
    "unfixable",
    "unfixed",
    "unflawed",
    "unfocused",
    "unfold",
    "unfounded",
    "unframed",
    "unfreeze",
    "unfrosted",
    "unfrozen",
    "unfunded",
    "unglazed",
    "ungloved",
    "unglue",
    "ungodly",
    "ungraded",
    "ungreased",
    "unguarded",
    "unguided",
    "unhappily",
    "unhappy",
    "unharmed",
    "unhealthy",
    "unheard",
    "unhearing",
    "unheated",
    "unhelpful",
    "unhidden",
    "unhinge",
    "unhitched",
    "unholy",
    "unhook",
    "unicorn",
    "unicycle",
    "unified",
    "unifier",
    "uniformed",
    "uniformly",
    "unify",
    "unimpeded",
    "uninjured",
    "uninstall",
    "uninsured",
    "uninvited",
    "union",
    "uniquely",
    "unisexual",
    "unison",
    "unissued",
    "unit",
    "universal",
    "universe",
    "unjustly",
    "unkempt",
    "unkind",
    "unknotted",
    "unknowing",
    "unknown",
    "unlaced",
    "unlatch",
    "unlawful",
    "unleaded",
    "unlearned",
    "unleash",
    "unless",
    "unleveled",
    "unlighted",
    "unlikable",
    "unlimited",
    "unlined",
    "unlinked",
    "unlisted",
    "unlit",
    "unlivable",
    "unloaded",
    "unloader",
    "unlocked",
    "unlocking",
    "unlovable",
    "unloved",
    "unlovely",
    "unloving",
    "unluckily",
    "unlucky",
    "unmade",
    "unmanaged",
    "unmanned",
    "unmapped",
    "unmarked",
    "unmasked",
    "unmasking",
    "unmatched",
    "unmindful",
    "unmixable",
    "unmixed",
    "unmolded",
    "unmoral",
    "unmovable",
    "unmoved",
    "unmoving",
    "unnamable",
    "unnamed",
    "unnatural",
    "unneeded",
    "unnerve",
    "unnerving",
    "unnoticed",
    "unopened",
    "unopposed",
    "unpack",
    "unpadded",
    "unpaid",
    "unpainted",
    "unpaired",
    "unpaved",
    "unpeeled",
    "unpicked",
    "unpiloted",
    "unpinned",
    "unplanned",
    "unplanted",
    "unpleased",
    "unpledged",
    "unplowed",
    "unplug",
    "unpopular",
    "unproven",
    "unquote",
    "unranked",
    "unrated",
    "unraveled",
    "unreached",
    "unread",
    "unreal",
    "unreeling",
    "unrefined",
    "unrelated",
    "unrented",
    "unrest",
    "unretired",
    "unrevised",
    "unrigged",
    "unripe",
    "unrivaled",
    "unroasted",
    "unrobed",
    "unroll",
    "unruffled",
    "unruly",
    "unrushed",
    "unsaddle",
    "unsafe",
    "unsaid",
    "unsalted",
    "unsaved",
    "unsavory",
    "unscathed",
    "unscented",
    "unscrew",
    "unsealed",
    "unseated",
    "unsecured",
    "unseeing",
    "unseemly",
    "unseen",
    "unselect",
    "unselfish",
    "unsent",
    "unsettled",
    "unshackle",
    "unshaken",
    "unshaved",
    "unshaven",
    "unsheathe",
    "unshipped",
    "unsightly",
    "unsigned",
    "unskilled",
    "unsliced",
    "unsmooth",
    "unsnap",
    "unsocial",
    "unsoiled",
    "unsold",
    "unsolved",
    "unsorted",
    "unspoiled",
    "unspoken",
    "unstable",
    "unstaffed",
    "unstamped",
    "unsteady",
    "unsterile",
    "unstirred",
    "unstitch",
    "unstopped",
    "unstuck",
    "unstuffed",
    "unstylish",
    "unsubtle",
    "unsubtly",
    "unsuited",
    "unsure",
    "unsworn",
    "untagged",
    "untainted",
    "untaken",
    "untamed",
    "untangled",
    "untapped",
    "untaxed",
    "unthawed",
    "unthread",
    "untidy",
    "untie",
    "until",
    "untimed",
    "untimely",
    "untitled",
    "untoasted",
    "untold",
    "untouched",
    "untracked",
    "untrained",
    "untreated",
    "untried",
    "untrimmed",
    "untrue",
    "untruth",
    "unturned",
    "untwist",
    "untying",
    "unusable",
    "unused",
    "unusual",
    "unvalued",
    "unvaried",
    "unvarying",
    "unveiled",
    "unveiling",
    "unvented",
    "unviable",
    "unvisited",
    "unvocal",
    "unwanted",
    "unwarlike",
    "unwary",
    "unwashed",
    "unwatched",
    "unweave",
    "unwed",
    "unwelcome",
    "unwell",
    "unwieldy",
    "unwilling",
    "unwind",
    "unwired",
    "unwitting",
    "unwomanly",
    "unworldly",
    "unworn",
    "unworried",
    "unworthy",
    "unwound",
    "unwoven",
    "unwrapped",
    "unwritten",
    "unzip",
    "upbeat",
    "upchuck",
    "upcoming",
    "upcountry",
    "update",
    "upfront",
    "upgrade",
    "upheaval",
    "upheld",
    "uphill",
    "uphold",
    "uplifted",
    "uplifting",
    "upload",
    "upon",
    "upper",
    "upright",
    "uprising",
    "upriver",
    "uproar",
    "uproot",
    "upscale",
    "upside",
    "upstage",
    "upstairs",
    "upstart",
    "upstate",
    "upstream",
    "upstroke",
    "upswing",
    "uptake",
    "uptight",
    "uptown",
    "upturned",
    "upward",
    "upwind",
    "uranium",
    "urban",
    "urchin",
    "urethane",
    "urgency",
    "urgent",
    "urging",
    "urologist",
    "urology",
    "usable",
    "usage",
    "useable",
    "used",
    "uselessly",
    "user",
    "usher",
    "usual",
    "utensil",
    "utility",
    "utilize",
    "utmost",
    "utopia",
    "utter",
    "vacancy",
    "vacant",
    "vacate",
    "vacation",
    "vagabond",
    "vagrancy",
    "vagrantly",
    "vaguely",
    "vagueness",
    "valiant",
    "valid",
    "valium",
    "valley",
    "valuables",
    "value",
    "vanilla",
    "vanish",
    "vanity",
    "vanquish",
    "vantage",
    "vaporizer",
    "variable",
    "variably",
    "varied",
    "variety",
    "various",
    "varmint",
    "varnish",
    "varsity",
    "varying",
    "vascular",
    "vaseline",
    "vastly",
    "vastness",
    "veal",
    "vegan",
    "veggie",
    "vehicular",
    "velcro",
    "velocity",
    "velvet",
    "vendetta",
    "vending",
    "vendor",
    "veneering",
    "vengeful",
    "venomous",
    "ventricle",
    "venture",
    "venue",
    "venus",
    "verbalize",
    "verbally",
    "verbose",
    "verdict",
    "verify",
    "verse",
    "version",
    "versus",
    "vertebrae",
    "vertical",
    "vertigo",
    "very",
    "vessel",
    "vest",
    "veteran",
    "veto",
    "vexingly",
    "viability",
    "viable",
    "vibes",
    "vice",
    "vicinity",
    "victory",
    "video",
    "viewable",
    "viewer",
    "viewing",
    "viewless",
    "viewpoint",
    "vigorous",
    "village",
    "villain",
    "vindicate",
    "vineyard",
    "vintage",
    "violate",
    "violation",
    "violator",
    "violet",
    "violin",
    "viper",
    "viral",
    "virtual",
    "virtuous",
    "virus",
    "visa",
    "viscosity",
    "viscous",
    "viselike",
    "visible",
    "visibly",
    "vision",
    "visiting",
    "visitor",
    "visor",
    "vista",
    "vitality",
    "vitalize",
    "vitally",
    "vitamins",
    "vivacious",
    "vividly",
    "vividness",
    "vixen",
    "vocalist",
    "vocalize",
    "vocally",
    "vocation",
    "voice",
    "voicing",
    "void",
    "volatile",
    "volley",
    "voltage",
    "volumes",
    "voter",
    "voting",
    "voucher",
    "vowed",
    "vowel",
    "voyage",
    "wackiness",
    "wad",
    "wafer",
    "waffle",
    "waged",
    "wager",
    "wages",
    "waggle",
    "wagon",
    "wake",
    "waking",
    "walk",
    "walmart",
    "walnut",
    "walrus",
    "waltz",
    "wand",
    "wannabe",
    "wanted",
    "wanting",
    "wasabi",
    "washable",
    "washbasin",
    "washboard",
    "washbowl",
    "washcloth",
    "washday",
    "washed",
    "washer",
    "washhouse",
    "washing",
    "washout",
    "washroom",
    "washstand",
    "washtub",
    "wasp",
    "wasting",
    "watch",
    "water",
    "waviness",
    "waving",
    "wavy",
    "whacking",
    "whacky",
    "wham",
    "wharf",
    "wheat",
    "whenever",
    "whiff",
    "whimsical",
    "whinny",
    "whiny",
    "whisking",
    "whoever",
    "whole",
    "whomever",
    "whoopee",
    "whooping",
    "whoops",
    "why",
    "wick",
    "widely",
    "widen",
    "widget",
    "widow",
    "width",
    "wieldable",
    "wielder",
    "wife",
    "wifi",
    "wikipedia",
    "wildcard",
    "wildcat",
    "wilder",
    "wildfire",
    "wildfowl",
    "wildland",
    "wildlife",
    "wildly",
    "wildness",
    "willed",
    "willfully",
    "willing",
    "willow",
    "willpower",
    "wilt",
    "wimp",
    "wince",
    "wincing",
    "wind",
    "wing",
    "winking",
    "winner",
    "winnings",
    "winter",
    "wipe",
    "wired",
    "wireless",
    "wiring",
    "wiry",
    "wisdom",
    "wise",
    "wish",
    "wisplike",
    "wispy",
    "wistful",
    "wizard",
    "wobble",
    "wobbling",
    "wobbly",
    "wok",
    "wolf",
    "wolverine",
    "womanhood",
    "womankind",
    "womanless",
    "womanlike",
    "womanly",
    "womb",
    "woof",
    "wooing",
    "wool",
    "woozy",
    "word",
    "work",
    "worried",
    "worrier",
    "worrisome",
    "worry",
    "worsening",
    "worshiper",
    "worst",
    "wound",
    "woven",
    "wow",
    "wrangle",
    "wrath",
    "wreath",
    "wreckage",
    "wrecker",
    "wrecking",
    "wrench",
    "wriggle",
    "wriggly",
    "wrinkle",
    "wrinkly",
    "wrist",
    "writing",
    "written",
    "wrongdoer",
    "wronged",
    "wrongful",
    "wrongly",
    "wrongness",
    "wrought",
    "xbox",
    "xerox",
    "yahoo",
    "yam",
    "yanking",
    "yapping",
    "yard",
    "yarn",
    "yeah",
    "yearbook",
    "yearling",
    "yearly",
    "yearning",
    "yeast",
    "yelling",
    "yelp",
    "yen",
    "yesterday",
    "yiddish",
    "yield",
    "yin",
    "yippee",
    "yo-yo",
    "yodel",
    "yoga",
    "yogurt",
    "yonder",
    "yoyo",
    "yummy",
    "zap",
    "zealous",
    "zebra",
    "zen",
    "zeppelin",
    "zero",
    "zestfully",
    "zesty",
    "zigzagged",
    "zipfile",
    "zipping",
    "zippy",
    "zips",
    "zit",
    "zodiac",
    "zombie",
    "zone",
    "zoning",
    "zookeeper",
    "zoologist",
    "zoology",
    "zoom",
];

;// ../../libs/common/src/platform/services/key-state/org-keys.state.ts

const bw_USER_ENCRYPTED_ORGANIZATION_KEYS = bw_UserKeyDefinition.record(bw_CRYPTO_DISK, "organizationKeys", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});

;// ../../libs/common/src/platform/services/key-state/provider-keys.state.ts

const bw_USER_ENCRYPTED_PROVIDER_KEYS = bw_UserKeyDefinition.record(bw_CRYPTO_DISK, "providerKeys", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});

;// ../../libs/common/src/platform/services/key-state/user-key.state.ts


const bw_USER_EVER_HAD_USER_KEY = new bw_UserKeyDefinition(bw_CRYPTO_DISK, "everHadUserKey", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});
const bw_USER_ENCRYPTED_PRIVATE_KEY = new bw_UserKeyDefinition(bw_CRYPTO_DISK, "privateKey", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});
const bw_USER_KEY = new bw_UserKeyDefinition(bw_CRYPTO_MEMORY, "userKey", {
    deserializer: (obj) => bw_SymmetricCryptoKey.fromJSON(obj),
    clearOn: ["logout", "lock"],
});

;// ../../libs/key-management/src/key.service.ts
var bw_key_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};















class bw_DefaultKeyService {
    constructor(pinService, masterPasswordService, keyGenerationService, cryptoFunctionService, encryptService, platformUtilService, logService, stateService, accountService, stateProvider, kdfConfigService) {
        this.pinService = pinService;
        this.masterPasswordService = masterPasswordService;
        this.keyGenerationService = keyGenerationService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.encryptService = encryptService;
        this.platformUtilService = platformUtilService;
        this.logService = logService;
        this.stateService = stateService;
        this.accountService = accountService;
        this.stateProvider = stateProvider;
        this.kdfConfigService = kdfConfigService;
        // User Key
        this.activeUserEverHadUserKey = stateProvider.getActive(bw_USER_EVER_HAD_USER_KEY);
        this.everHadUserKey$ = this.activeUserEverHadUserKey.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : false));
        this.activeUserOrgKeys$ = this.stateProvider.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => (userId != null ? this.orgKeys$(userId) : bw_external_rxjs_namespaceObject.NEVER)));
    }
    setUserKey(key, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                throw new Error("No key provided. Lock the user to clear the key");
            }
            if (userId == null) {
                throw new Error("No userId provided.");
            }
            // Set userId to ensure we have one for the account status update
            yield this.stateProvider.setUserState(bw_USER_KEY, key, userId);
            yield this.stateProvider.setUserState(bw_USER_EVER_HAD_USER_KEY, true, userId);
            yield this.storeAdditionalKeys(key, userId);
        });
    }
    setUserKeys(userKey, encPrivateKey, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (userKey == null) {
                throw new Error("No userKey provided. Lock the user to clear the key");
            }
            if (encPrivateKey == null) {
                throw new Error("No encPrivateKey provided.");
            }
            if (userId == null) {
                throw new Error("No userId provided.");
            }
            const decryptedPrivateKey = yield this.decryptPrivateKey(encPrivateKey, userKey);
            if (decryptedPrivateKey == null) {
                throw new bw_UserPrivateKeyDecryptionFailedError();
            }
            yield this.setUserKey(userKey, userId);
            yield this.setPrivateKey(encPrivateKey, userId);
        });
    }
    refreshAdditionalKeys() {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            if (activeUserId == null) {
                throw new Error("Can only refresh keys while there is an active user.");
            }
            const key = yield this.getUserKey(activeUserId);
            yield this.setUserKey(key, activeUserId);
        });
    }
    getInMemoryUserKeyFor$(userId) {
        return this.stateProvider.getUserState$(bw_USER_KEY, userId);
    }
    getUserKey(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const userKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_USER_KEY, userId));
            return userKey;
        });
    }
    isLegacyUser(masterKey, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("No active user id found.");
            }
            masterKey !== null && masterKey !== void 0 ? masterKey : (masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId)));
            return yield this.validateUserKey(masterKey, userId);
        });
    }
    // TODO: legacy support for user key is no longer needed since we require users to migrate on login
    getUserKeyWithLegacySupport(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("No active user id found.");
            }
            const userKey = yield this.getUserKey(userId);
            if (userKey) {
                return userKey;
            }
            // Legacy support: encryption used to be done with the master key (derived from master password).
            // Users who have not migrated will have a null user key and must use the master key instead.
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            return masterKey;
        });
    }
    getUserKeyFromStorage(keySuffix, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("No active user id found.");
            }
            const userKey = yield this.getKeyFromStorage(keySuffix, userId);
            if (userKey == null) {
                return null;
            }
            if (!(yield this.validateUserKey(userKey, userId))) {
                this.logService.warning("Invalid key, throwing away stored keys");
                yield this.clearAllStoredUserKeys(userId);
            }
            return userKey;
        });
    }
    hasUserKey(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                return false;
            }
            return yield this.hasUserKeyInMemory(userId);
        });
    }
    hasUserKeyInMemory(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                return false;
            }
            return (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_USER_KEY, userId))) != null;
        });
    }
    hasUserKeyStored(keySuffix, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.getKeyFromStorage(keySuffix, userId)) != null;
        });
    }
    makeUserKey(masterKey) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (masterKey == null) {
                const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
                if (userId == null) {
                    throw new Error("No active user id found.");
                }
                masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            }
            if (masterKey == null) {
                throw new Error("No Master Key found.");
            }
            const newUserKey = yield this.keyGenerationService.createKey(512);
            return this.buildProtectedSymmetricKey(masterKey, newUserKey.key);
        });
    }
    /**
     * Clears the user key. Clears all stored versions of the user keys as well, such as the biometrics key
     * @param userId The desired user
     */
    clearUserKey(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                // nothing to do
                return;
            }
            // Set userId to ensure we have one for the account status update
            yield this.stateProvider.setUserState(bw_USER_KEY, null, userId);
            yield this.clearAllStoredUserKeys(userId);
        });
    }
    clearStoredUserKey(keySuffix, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (keySuffix === bw_KeySuffixOptions.Auto) {
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.stateService.setUserKeyAutoUnlock(null, { userId: userId });
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.clearDeprecatedKeys(bw_KeySuffixOptions.Auto, userId);
            }
            if (keySuffix === bw_KeySuffixOptions.Pin && userId != null) {
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                this.pinService.clearPinKeyEncryptedUserKeyEphemeral(userId);
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.clearDeprecatedKeys(bw_KeySuffixOptions.Pin, userId);
            }
        });
    }
    setMasterKeyEncryptedUserKey(userKeyMasterKey, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("No active user id found.");
            }
            yield this.masterPasswordService.setMasterKeyEncryptedUserKey(new bw_enc_string_EncString(userKeyMasterKey), userId);
        });
    }
    // TODO: Move to MasterPasswordService
    getOrDeriveMasterKey(password, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const [resolvedUserId, email] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)((0,bw_external_rxjs_namespaceObject.combineLatest)([this.accountService.activeAccount$, this.accountService.accounts$]).pipe((0,bw_external_rxjs_namespaceObject.map)(([activeAccount, accounts]) => {
                userId !== null && userId !== void 0 ? userId : (userId = activeAccount === null || activeAccount === void 0 ? void 0 : activeAccount.id);
                if (userId == null || accounts[userId] == null) {
                    throw new Error("No user found");
                }
                return [userId, accounts[userId].email];
            })));
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(resolvedUserId));
            return (masterKey ||
                (yield this.makeMasterKey(password, email, yield this.kdfConfigService.getKdfConfig())));
        });
    }
    /**
     * Derive a master key from a password and email.
     *
     * @remarks
     * Does not validate the kdf config to ensure it satisfies the minimum requirements for the given kdf type.
     * TODO: Move to MasterPasswordService
     */
    makeMasterKey(password, email, KdfConfig) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.keyGenerationService.deriveKeyFromPassword(password, email, KdfConfig));
        });
    }
    encryptUserKeyWithMasterKey(masterKey, userKey) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userKey || (userKey = yield this.getUserKey());
            return yield this.buildProtectedSymmetricKey(masterKey, userKey.key);
        });
    }
    // TODO: move to MasterPasswordService
    hashMasterKey(password, key, hashPurpose) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
                if (userId == null) {
                    throw new Error("No active user found.");
                }
                key = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            }
            if (password == null || key == null) {
                throw new Error("Invalid parameters.");
            }
            const iterations = hashPurpose === bw_HashPurpose.LocalAuthorization ? 2 : 1;
            const hash = yield this.cryptoFunctionService.pbkdf2(key.key, password, "sha256", iterations);
            return bw_utils_Utils.fromBufferToB64(hash);
        });
    }
    // TODO: move to MasterPasswordService
    compareKeyHash(masterPassword, masterKey, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (masterKey == null) {
                throw new Error("'masterKey' is required to be non-null.");
            }
            if (masterPassword == null) {
                // If they don't give us a master password, we can't hash it, and therefore
                // it will never match what we have stored.
                return false;
            }
            // Retrieve the current password hash
            const storedPasswordHash = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKeyHash$(userId));
            if (storedPasswordHash == null) {
                return false;
            }
            // Hash the key for local use
            const localKeyHash = yield this.hashMasterKey(masterPassword, masterKey, bw_HashPurpose.LocalAuthorization);
            // Check if the stored hash is already equal to the hash we create locally
            if (localKeyHash == null || storedPasswordHash !== localKeyHash) {
                return false;
            }
            return true;
        });
    }
    setOrgKeys(orgs, providerOrgs, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_ORGANIZATION_KEYS).update(() => {
                const encOrgKeyData = {};
                for (const org of orgs) {
                    encOrgKeyData[org.id] = {
                        type: "organization",
                        key: org.key,
                    };
                }
                for (const org of providerOrgs) {
                    encOrgKeyData[org.id] = {
                        type: "provider",
                        providerId: org.providerId,
                        key: org.key,
                    };
                }
                return encOrgKeyData;
            });
        });
    }
    getOrgKey(orgId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            if (activeUserId == null) {
                throw new Error("A user must be active to retrieve an org key");
            }
            const orgKeys = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.orgKeys$(activeUserId));
            return (_a = orgKeys === null || orgKeys === void 0 ? void 0 : orgKeys[orgId]) !== null && _a !== void 0 ? _a : null;
        });
    }
    makeDataEncKey(key) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                throw new Error("No key provided");
            }
            const newSymKey = yield this.keyGenerationService.createKey(512);
            return this.buildProtectedSymmetricKey(key, newSymKey.key);
        });
    }
    clearOrgKeys(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                // nothing to do
                return;
            }
            yield this.stateProvider.setUserState(bw_USER_ENCRYPTED_ORGANIZATION_KEYS, null, userId);
        });
    }
    setProviderKeys(providers, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_PROVIDER_KEYS).update(() => {
                const encProviderKeys = {};
                providers.forEach((provider) => {
                    encProviderKeys[provider.id] = provider.key;
                });
                return encProviderKeys;
            });
        });
    }
    // TODO: Deprecate in favor of observable
    getProviderKey(providerId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            if (providerId == null) {
                return null;
            }
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            if (activeUserId == null) {
                throw new Error("No active user found.");
            }
            const providerKeys = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.providerKeys$(activeUserId));
            return (_a = providerKeys === null || providerKeys === void 0 ? void 0 : providerKeys[providerId]) !== null && _a !== void 0 ? _a : null;
        });
    }
    clearProviderKeys(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                // nothing to do
                return;
            }
            yield this.stateProvider.setUserState(bw_USER_ENCRYPTED_PROVIDER_KEYS, null, userId);
        });
    }
    // TODO: Make userId required
    makeOrgKey(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const shareKey = yield this.keyGenerationService.createKey(512);
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("No active user found.");
            }
            const publicKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userPublicKey$(userId));
            if (publicKey == null) {
                throw new Error("No public key found.");
            }
            const encShareKey = yield this.encryptService.rsaEncrypt(shareKey.key, publicKey);
            return [encShareKey, shareKey];
        });
    }
    setPrivateKey(encPrivateKey, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (encPrivateKey == null) {
                return;
            }
            yield this.stateProvider
                .getUser(userId, bw_USER_ENCRYPTED_PRIVATE_KEY)
                .update(() => encPrivateKey);
        });
    }
    getPrivateKey() {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            if (activeUserId == null) {
                throw new Error("User must be active while attempting to retrieve private key.");
            }
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userPrivateKey$(activeUserId));
        });
    }
    // TODO: Make public key required
    getFingerprint(fingerprintMaterial, publicKey) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (publicKey == null) {
                const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
                if (activeUserId == null) {
                    throw new Error("No active user found.");
                }
                publicKey = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userPublicKey$(activeUserId)));
            }
            if (publicKey === null) {
                throw new Error("No public key available.");
            }
            const keyFingerprint = yield this.cryptoFunctionService.hash(publicKey, "sha256");
            const userFingerprint = yield this.cryptoFunctionService.hkdfExpand(keyFingerprint, fingerprintMaterial, 32, "sha256");
            return this.hashPhrase(userFingerprint);
        });
    }
    makeKeyPair(key) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                throw new Error("'key' is a required parameter and must be non-null.");
            }
            const keyPair = yield this.cryptoFunctionService.rsaGenerateKeyPair(2048);
            const publicB64 = bw_utils_Utils.fromBufferToB64(keyPair[0]);
            const privateEnc = yield this.encryptService.encrypt(keyPair[1], key);
            return [publicB64, privateEnc];
        });
    }
    /**
     * Clears the user's key pair
     * @param userId The desired user
     */
    clearKeyPair(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_USER_ENCRYPTED_PRIVATE_KEY, null, userId);
        });
    }
    clearPinKeys(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("Cannot clear PIN keys, no user Id resolved.");
            }
            yield this.pinService.clearPinKeyEncryptedUserKeyPersistent(userId);
            yield this.pinService.clearPinKeyEncryptedUserKeyEphemeral(userId);
            yield this.pinService.clearUserKeyEncryptedPin(userId);
            yield this.clearDeprecatedKeys(bw_KeySuffixOptions.Pin, userId);
        });
    }
    makeSendKey(keyMaterial) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            return yield this.keyGenerationService.deriveKeyFromMaterial(keyMaterial, "bitwarden-send", "send");
        });
    }
    makeCipherKey() {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.keyGenerationService.createKey(512));
        });
    }
    clearKeys(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            if (userId == null) {
                throw new Error("Cannot clear keys, no user Id resolved.");
            }
            yield this.masterPasswordService.clearMasterKeyHash(userId);
            yield this.clearUserKey(userId);
            yield this.clearOrgKeys(userId);
            yield this.clearProviderKeys(userId);
            yield this.clearKeyPair(userId);
            yield this.clearPinKeys(userId);
            yield this.stateProvider.setUserState(bw_USER_EVER_HAD_USER_KEY, null, userId);
        });
    }
    // EFForg/OpenWireless
    // ref https://github.com/EFForg/OpenWireless/blob/master/app/js/diceware.js
    randomNumber(min, max) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            let rval = 0;
            const range = max - min + 1;
            const bitsNeeded = Math.ceil(Math.log2(range));
            if (bitsNeeded > 53) {
                throw new Error("We cannot generate numbers larger than 53 bits.");
            }
            const bytesNeeded = Math.ceil(bitsNeeded / 8);
            const mask = Math.pow(2, bitsNeeded) - 1;
            // 7776 -> (2^13 = 8192) -1 == 8191 or 0x00001111 11111111
            // Fill a byte array with N random numbers
            const byteArray = new Uint8Array(yield this.cryptoFunctionService.randomBytes(bytesNeeded));
            let p = (bytesNeeded - 1) * 8;
            for (let i = 0; i < bytesNeeded; i++) {
                rval += byteArray[i] * Math.pow(2, p);
                p -= 8;
            }
            // Use & to apply the mask and reduce the number of recursive lookups
            rval = rval & mask;
            if (rval >= range) {
                // Integer out of acceptable range
                return this.randomNumber(min, max);
            }
            // Return an integer that falls within the range
            return min + rval;
        });
    }
    // ---HELPERS---
    validateUserKey(key, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                return false;
            }
            try {
                const encPrivateKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_PRIVATE_KEY).state$);
                if (encPrivateKey == null) {
                    return false;
                }
                // Can decrypt private key
                const privateKey = yield this.decryptPrivateKey(encPrivateKey, key);
                if (privateKey == null) {
                    // failed to decrypt
                    return false;
                }
                // Can successfully derive public key
                const publicKey = yield this.derivePublicKey(privateKey);
                if (publicKey == null) {
                    // failed to decrypt
                    return false;
                }
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                return false;
            }
            return true;
        });
    }
    /**
     * Initialize all necessary crypto keys needed for a new account.
     * Warning! This completely replaces any existing keys!
     */
    initAccount() {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            if (activeUserId == null) {
                throw new Error("Cannot initilize an account if one is not active.");
            }
            // Verify user key doesn't exist
            const existingUserKey = yield this.getUserKey(activeUserId);
            if (existingUserKey != null) {
                this.logService.error("Tried to initialize account with existing user key.");
                throw new Error("Cannot initialize account, keys already exist.");
            }
            const userKey = (yield this.keyGenerationService.createKey(512));
            const [publicKey, privateKey] = yield this.makeKeyPair(userKey);
            if (privateKey.encryptedString == null) {
                throw new Error("Failed to create valid private key.");
            }
            yield this.setUserKey(userKey, activeUserId);
            yield this.stateProvider
                .getUser(activeUserId, bw_USER_ENCRYPTED_PRIVATE_KEY)
                .update(() => privateKey.encryptedString);
            return {
                userKey,
                publicKey,
                privateKey,
            };
        });
    }
    /**
     * Generates any additional keys if needed. Additional keys are
     * keys such as biometrics, auto, and pin keys.
     * Useful to make sure other keys stay in sync when the user key
     * has been rotated.
     * @param key The user key
     * @param userId The desired user
     */
    storeAdditionalKeys(key, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            const storeAuto = yield this.shouldStoreKey(bw_KeySuffixOptions.Auto, userId);
            if (storeAuto) {
                yield this.stateService.setUserKeyAutoUnlock(key.keyB64, { userId: userId });
            }
            else {
                yield this.stateService.setUserKeyAutoUnlock(null, { userId: userId });
            }
            yield this.clearDeprecatedKeys(bw_KeySuffixOptions.Auto, userId);
            const storePin = yield this.shouldStoreKey(bw_KeySuffixOptions.Pin, userId);
            if (storePin) {
                // Decrypt userKeyEncryptedPin with user key
                const pin = yield this.encryptService.decryptToUtf8((yield this.pinService.getUserKeyEncryptedPin(userId)), key);
                const pinKeyEncryptedUserKey = yield this.pinService.createPinKeyEncryptedUserKey(pin, key, userId);
                const noPreExistingPersistentKey = (yield this.pinService.getPinKeyEncryptedUserKeyPersistent(userId)) == null;
                yield this.pinService.storePinKeyEncryptedUserKey(pinKeyEncryptedUserKey, noPreExistingPersistentKey, userId);
                // We can't always clear deprecated keys because the pin is only
                // migrated once used to unlock
                yield this.clearDeprecatedKeys(bw_KeySuffixOptions.Pin, userId);
            }
            else {
                yield this.pinService.clearPinKeyEncryptedUserKeyPersistent(userId);
                yield this.pinService.clearPinKeyEncryptedUserKeyEphemeral(userId);
            }
        });
    }
    shouldStoreKey(keySuffix, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            let shouldStoreKey = false;
            switch (keySuffix) {
                case bw_KeySuffixOptions.Auto: {
                    // TODO: Sharing the UserKeyDefinition is temporary to get around a circ dep issue between
                    // the VaultTimeoutSettingsSvc and this service.
                    // This should be fixed as part of the PM-7082 - Auto Key Service work.
                    const vaultTimeout = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_VAULT_TIMEOUT, userId));
                    shouldStoreKey = vaultTimeout == bw_VaultTimeoutStringType.Never;
                    break;
                }
                case bw_KeySuffixOptions.Pin: {
                    const userKeyEncryptedPin = yield this.pinService.getUserKeyEncryptedPin(userId);
                    shouldStoreKey = !!userKeyEncryptedPin;
                    break;
                }
            }
            return shouldStoreKey;
        });
    }
    getKeyFromStorage(keySuffix, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (keySuffix === bw_KeySuffixOptions.Auto) {
                const userKey = yield this.stateService.getUserKeyAutoUnlock({ userId: userId });
                if (userKey) {
                    return new bw_SymmetricCryptoKey(bw_utils_Utils.fromB64ToArray(userKey));
                }
            }
            return null;
        });
    }
    clearAllStoredUserKeys(userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateService.setUserKeyAutoUnlock(null, { userId: userId });
            yield this.pinService.clearPinKeyEncryptedUserKeyEphemeral(userId);
        });
    }
    hashPhrase(hash_1) {
        return bw_key_service_awaiter(this, arguments, void 0, function* (hash, minimumEntropy = 64) {
            const entropyPerWord = Math.log(bw_EFFLongWordList.length) / Math.log(2);
            let numWords = Math.ceil(minimumEntropy / entropyPerWord);
            const hashArr = Array.from(new Uint8Array(hash));
            const entropyAvailable = hashArr.length * 4;
            if (numWords * entropyPerWord > entropyAvailable) {
                throw new Error("Output entropy of hash function is too small");
            }
            const phrase = [];
            let hashNumber = bw_external_big_integer_namespaceObject.fromArray(hashArr, 256);
            while (numWords--) {
                const remainder = hashNumber.mod(bw_EFFLongWordList.length);
                hashNumber = hashNumber.divide(bw_EFFLongWordList.length);
                phrase.push(bw_EFFLongWordList[remainder]);
            }
            return phrase;
        });
    }
    buildProtectedSymmetricKey(encryptionKey, newSymKey) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            let protectedSymKey;
            if (encryptionKey.key.byteLength === 32) {
                const stretchedEncryptionKey = yield this.keyGenerationService.stretchKey(encryptionKey);
                protectedSymKey = yield this.encryptService.encrypt(newSymKey, stretchedEncryptionKey);
            }
            else if (encryptionKey.key.byteLength === 64) {
                protectedSymKey = yield this.encryptService.encrypt(newSymKey, encryptionKey);
            }
            else {
                throw new Error("Invalid key size.");
            }
            return [new bw_SymmetricCryptoKey(newSymKey), protectedSymKey];
        });
    }
    // --LEGACY METHODS--
    // We previously used the master key for additional keys, but now we use the user key.
    // These methods support migrating the old keys to the new ones.
    // TODO: Remove after 2023.10 release (https://bitwarden.atlassian.net/browse/PM-3475)
    clearDeprecatedKeys(keySuffix, userId) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (keySuffix === bw_KeySuffixOptions.Auto) {
                yield this.stateService.setCryptoMasterKeyAuto(null, { userId: userId });
            }
            else if (keySuffix === bw_KeySuffixOptions.Pin && userId != null) {
                yield this.pinService.clearOldPinKeyEncryptedMasterKey(userId);
            }
        });
    }
    userKey$(userId) {
        return this.stateProvider.getUser(userId, bw_USER_KEY).state$;
    }
    userKeyWithLegacySupport$(userId) {
        return this.userKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userKey) => {
            if (userKey != null) {
                return (0,bw_external_rxjs_namespaceObject.of)(userKey);
            }
            // Legacy path
            return this.masterPasswordService.masterKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.switchMap)((masterKey) => bw_key_service_awaiter(this, void 0, void 0, function* () {
                if (!(yield this.validateUserKey(masterKey, userId))) {
                    // We don't have a UserKey or a valid MasterKey
                    return null;
                }
                // The master key is valid meaning, the org keys and such are encrypted with this key
                return masterKey;
            })));
        }));
    }
    userPublicKey$(userId) {
        return this.userPrivateKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.switchMap)((pk) => bw_key_service_awaiter(this, void 0, void 0, function* () { return yield this.derivePublicKey(pk); })));
    }
    derivePublicKey(privateKey) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (privateKey == null) {
                return null;
            }
            return (yield this.cryptoFunctionService.rsaExtractPublicKey(privateKey));
        });
    }
    userPrivateKey$(userId) {
        return this.userPrivateKeyHelper$(userId, false).pipe((0,bw_external_rxjs_namespaceObject.map)((keys) => { var _a; return (_a = keys === null || keys === void 0 ? void 0 : keys.userPrivateKey) !== null && _a !== void 0 ? _a : null; }));
    }
    userEncryptedPrivateKey$(userId) {
        return this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_PRIVATE_KEY).state$;
    }
    userPrivateKeyWithLegacySupport$(userId) {
        return this.userPrivateKeyHelper$(userId, true).pipe((0,bw_external_rxjs_namespaceObject.map)((keys) => { var _a; return (_a = keys === null || keys === void 0 ? void 0 : keys.userPrivateKey) !== null && _a !== void 0 ? _a : null; }));
    }
    userPrivateKeyHelper$(userId, legacySupport) {
        const userKey$ = legacySupport ? this.userKeyWithLegacySupport$(userId) : this.userKey$(userId);
        return userKey$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userKey) => {
            if (userKey == null) {
                return (0,bw_external_rxjs_namespaceObject.of)(null);
            }
            return this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_PRIVATE_KEY).state$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((encryptedPrivateKey) => bw_key_service_awaiter(this, void 0, void 0, function* () { return yield this.decryptPrivateKey(encryptedPrivateKey, userKey); })), 
            // Combine outerscope info with user private key
            (0,bw_external_rxjs_namespaceObject.map)((userPrivateKey) => ({
                userKey,
                userPrivateKey,
            })));
        }));
    }
    decryptPrivateKey(encryptedPrivateKey, key) {
        return bw_key_service_awaiter(this, void 0, void 0, function* () {
            if (encryptedPrivateKey == null) {
                return null;
            }
            return (yield this.encryptService.decryptToBytes(new bw_enc_string_EncString(encryptedPrivateKey), key, "Content: Encrypted Private Key"));
        });
    }
    providerKeys$(userId) {
        return this.userPrivateKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userPrivateKey) => {
            if (userPrivateKey == null) {
                return (0,bw_external_rxjs_namespaceObject.of)(null);
            }
            return this.providerKeysHelper$(userId, userPrivateKey);
        }));
    }
    /**
     * A helper for decrypting provider keys that requires a user id and that users decrypted private key
     * this is helpful for when you may have already grabbed the user private key and don't want to redo
     * that work to get the provider keys.
     */
    providerKeysHelper$(userId, userPrivateKey) {
        return this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_PROVIDER_KEYS).state$.pipe(
        // Convert each value in the record to it's own decryption observable
        bw_convertValues((_, value) => bw_key_service_awaiter(this, void 0, void 0, function* () {
            const decrypted = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(value), userPrivateKey);
            return new bw_SymmetricCryptoKey(decrypted);
        })), 
        // switchMap since there are no side effects
        (0,bw_external_rxjs_namespaceObject.switchMap)((encryptedProviderKeys) => {
            if (encryptedProviderKeys == null) {
                return (0,bw_external_rxjs_namespaceObject.of)(null);
            }
            // Can't give an empty record to forkJoin
            if (Object.keys(encryptedProviderKeys).length === 0) {
                return (0,bw_external_rxjs_namespaceObject.of)({});
            }
            return (0,bw_external_rxjs_namespaceObject.forkJoin)(encryptedProviderKeys);
        }));
    }
    orgKeys$(userId) {
        return this.cipherDecryptionKeys$(userId, true).pipe((0,bw_external_rxjs_namespaceObject.map)((keys) => { var _a; return (_a = keys === null || keys === void 0 ? void 0 : keys.orgKeys) !== null && _a !== void 0 ? _a : null; }));
    }
    encryptedOrgKeys$(userId) {
        return this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_ORGANIZATION_KEYS).state$;
    }
    cipherDecryptionKeys$(userId, legacySupport = false) {
        var _a;
        return (_a = this.userPrivateKeyHelper$(userId, legacySupport)) === null || _a === void 0 ? void 0 : _a.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userKeys) => {
            if (userKeys == null) {
                return (0,bw_external_rxjs_namespaceObject.of)(null);
            }
            const userPrivateKey = userKeys.userPrivateKey;
            if (userPrivateKey == null) {
                // We can't do any org based decryption
                return (0,bw_external_rxjs_namespaceObject.of)({ userKey: userKeys.userKey, orgKeys: null });
            }
            return (0,bw_external_rxjs_namespaceObject.combineLatest)([
                this.stateProvider.getUser(userId, bw_USER_ENCRYPTED_ORGANIZATION_KEYS).state$,
                this.providerKeysHelper$(userId, userPrivateKey),
            ]).pipe((0,bw_external_rxjs_namespaceObject.switchMap)((_a) => bw_key_service_awaiter(this, [_a], void 0, function* ([encryptedOrgKeys, providerKeys]) {
                const result = {};
                encryptedOrgKeys = encryptedOrgKeys !== null && encryptedOrgKeys !== void 0 ? encryptedOrgKeys : {};
                for (const orgId of Object.keys(encryptedOrgKeys)) {
                    if (result[orgId] != null) {
                        continue;
                    }
                    const encrypted = bw_BaseEncryptedOrganizationKey.fromData(encryptedOrgKeys[orgId]);
                    if (encrypted == null) {
                        continue;
                    }
                    let decrypted;
                    if (bw_BaseEncryptedOrganizationKey.isProviderEncrypted(encrypted)) {
                        if (providerKeys == null) {
                            throw new Error("No provider keys found.");
                        }
                        decrypted = yield encrypted.decrypt(this.encryptService, providerKeys);
                    }
                    else {
                        decrypted = yield encrypted.decrypt(this.encryptService, userPrivateKey);
                    }
                    result[orgId] = decrypted;
                }
                return result;
            })), 
            // Combine them back together
            (0,bw_external_rxjs_namespaceObject.map)((orgKeys) => ({ userKey: userKeys.userKey, orgKeys: orgKeys })));
        }));
    }
}

;// ../../libs/common/src/platform/misc/range-with-default.ts
/**
 * A range with a default value.
 *
 * Enforces constraints to ensure min > default > max.
 */
class bw_RangeWithDefault {
    constructor(min, max, defaultValue) {
        this.min = min;
        this.max = max;
        this.defaultValue = defaultValue;
        if (min > max) {
            throw new Error(`${min} is greater than ${max}.`);
        }
        if (this.inRange(defaultValue) === false) {
            throw new Error("Default value is not in range.");
        }
    }
    inRange(value) {
        return value >= this.min && value <= this.max;
    }
}

;// ../../libs/key-management/src/enums/kdf-type.enum.ts
var bw_KdfType;
(function (KdfType) {
    KdfType[KdfType["PBKDF2_SHA256"] = 0] = "PBKDF2_SHA256";
    KdfType[KdfType["Argon2id"] = 1] = "Argon2id";
})(bw_KdfType || (bw_KdfType = {}));

;// ../../libs/key-management/src/models/kdf-config.ts


/**
 * Password-Based Key Derivation Function 2 (PBKDF2) KDF configuration.
 */
class bw_PBKDF2KdfConfig {
    constructor(iterations) {
        this.kdfType = bw_KdfType.PBKDF2_SHA256;
        this.iterations = iterations !== null && iterations !== void 0 ? iterations : bw_PBKDF2KdfConfig.ITERATIONS.defaultValue;
    }
    /**
     * Validates the PBKDF2 KDF configuration for updating the KDF config.
     * A Valid PBKDF2 KDF configuration has KDF iterations between the 600_000 and 2_000_000.
     */
    validateKdfConfigForSetting() {
        if (!bw_PBKDF2KdfConfig.ITERATIONS.inRange(this.iterations)) {
            throw new Error(`PBKDF2 iterations must be between ${bw_PBKDF2KdfConfig.ITERATIONS.min} and ${bw_PBKDF2KdfConfig.ITERATIONS.max}`);
        }
    }
    /**
     * Validates the PBKDF2 KDF configuration for pre-login.
     * A Valid PBKDF2 KDF configuration has KDF iterations between the 5000 and 2_000_000.
     */
    validateKdfConfigForPrelogin() {
        if (bw_PBKDF2KdfConfig.PRELOGIN_ITERATIONS_MIN > this.iterations) {
            throw new Error(`PBKDF2 iterations must be at least ${bw_PBKDF2KdfConfig.PRELOGIN_ITERATIONS_MIN}, but was ${this.iterations}; possible pre-login downgrade attack detected.`);
        }
    }
    static fromJSON(json) {
        return new bw_PBKDF2KdfConfig(json.iterations);
    }
}
bw_PBKDF2KdfConfig.ITERATIONS = new bw_RangeWithDefault(600000, 2000000, 600000);
bw_PBKDF2KdfConfig.PRELOGIN_ITERATIONS_MIN = 5000;
/**
 * Argon2 KDF configuration.
 */
class bw_Argon2KdfConfig {
    constructor(iterations, memory, parallelism) {
        this.kdfType = bw_KdfType.Argon2id;
        this.iterations = iterations !== null && iterations !== void 0 ? iterations : bw_Argon2KdfConfig.ITERATIONS.defaultValue;
        this.memory = memory !== null && memory !== void 0 ? memory : bw_Argon2KdfConfig.MEMORY.defaultValue;
        this.parallelism = parallelism !== null && parallelism !== void 0 ? parallelism : bw_Argon2KdfConfig.PARALLELISM.defaultValue;
    }
    /**
     * Validates the Argon2 KDF configuration for updating the KDF config.
     * A Valid Argon2 KDF configuration has iterations between 2 and 10, memory between 16mb and 1024mb, and parallelism between 1 and 16.
     */
    validateKdfConfigForSetting() {
        if (!bw_Argon2KdfConfig.ITERATIONS.inRange(this.iterations)) {
            throw new Error(`Argon2 iterations must be between ${bw_Argon2KdfConfig.ITERATIONS.min} and ${bw_Argon2KdfConfig.ITERATIONS.max}`);
        }
        if (!bw_Argon2KdfConfig.MEMORY.inRange(this.memory)) {
            throw new Error(`Argon2 memory must be between ${bw_Argon2KdfConfig.MEMORY.min} MiB and ${bw_Argon2KdfConfig.MEMORY.max} MiB`);
        }
        if (!bw_Argon2KdfConfig.PARALLELISM.inRange(this.parallelism)) {
            throw new Error(`Argon2 parallelism must be between ${bw_Argon2KdfConfig.PARALLELISM.min} and ${bw_Argon2KdfConfig.PARALLELISM.max}.`);
        }
    }
    /**
     * Validates the Argon2 KDF configuration for pre-login.
     */
    validateKdfConfigForPrelogin() {
        if (bw_Argon2KdfConfig.PRELOGIN_ITERATIONS_MIN > this.iterations) {
            throw new Error(`Argon2 iterations must be at least ${bw_Argon2KdfConfig.PRELOGIN_ITERATIONS_MIN}, but was ${this.iterations}; possible pre-login downgrade attack detected.`);
        }
        if (bw_Argon2KdfConfig.PRELOGIN_MEMORY_MIN > this.memory) {
            throw new Error(`Argon2 memory must be at least ${bw_Argon2KdfConfig.PRELOGIN_MEMORY_MIN} MiB, but was ${this.memory} MiB; possible pre-login downgrade attack detected.`);
        }
        if (bw_Argon2KdfConfig.PRELOGIN_PARALLELISM_MIN > this.parallelism) {
            throw new Error(`Argon2 parallelism must be at least ${bw_Argon2KdfConfig.PRELOGIN_PARALLELISM_MIN}, but was ${this.parallelism}; possible pre-login downgrade attack detected.`);
        }
    }
    static fromJSON(json) {
        return new bw_Argon2KdfConfig(json.iterations, json.memory, json.parallelism);
    }
}
bw_Argon2KdfConfig.MEMORY = new bw_RangeWithDefault(16, 1024, 64);
bw_Argon2KdfConfig.PARALLELISM = new bw_RangeWithDefault(1, 16, 4);
bw_Argon2KdfConfig.ITERATIONS = new bw_RangeWithDefault(2, 10, 3);
bw_Argon2KdfConfig.PRELOGIN_MEMORY_MIN = 16;
bw_Argon2KdfConfig.PRELOGIN_PARALLELISM_MIN = 1;
bw_Argon2KdfConfig.PRELOGIN_ITERATIONS_MIN = 2;
const bw_DEFAULT_KDF_CONFIG = new bw_PBKDF2KdfConfig(bw_PBKDF2KdfConfig.ITERATIONS.defaultValue);

;// ../../libs/key-management/src/kdf-config.service.ts
var bw_kdf_config_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




const bw_KDF_CONFIG = new bw_UserKeyDefinition(bw_KDF_CONFIG_DISK, "kdfConfig", {
    deserializer: (kdfConfig) => {
        if (kdfConfig == null) {
            return null;
        }
        return kdfConfig.kdfType === bw_KdfType.PBKDF2_SHA256
            ? bw_PBKDF2KdfConfig.fromJSON(kdfConfig)
            : bw_Argon2KdfConfig.fromJSON(kdfConfig);
    },
    clearOn: ["logout"],
});
class bw_DefaultKdfConfigService {
    constructor(stateProvider) {
        this.stateProvider = stateProvider;
    }
    setKdfConfig(userId, kdfConfig) {
        return bw_kdf_config_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("userId cannot be null");
            }
            if (kdfConfig == null) {
                throw new Error("kdfConfig cannot be null");
            }
            yield this.stateProvider.setUserState(bw_KDF_CONFIG, kdfConfig, userId);
        });
    }
    getKdfConfig() {
        return bw_kdf_config_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            if (userId == null) {
                throw new Error("KdfConfig can only be retrieved when there is active user");
            }
            const state = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_KDF_CONFIG).state$);
            if (state == null) {
                throw new Error("KdfConfig for active user account state is null");
            }
            return state;
        });
    }
    getKdfConfig$(userId) {
        if (userId == null) {
            throw new Error("userId cannot be null");
        }
        return this.stateProvider.getUser(userId, bw_KDF_CONFIG).state$;
    }
}

;// ../../libs/common/src/enums/feature-flag.enum.ts
/**
 * Feature flags.
 *
 * Flags MUST be short lived and SHALL be removed once enabled.
 */
var bw_feature_flag_enum_FeatureFlag;
(function (FeatureFlag) {
    /* Admin Console Team */
    FeatureFlag["AccountDeprovisioning"] = "pm-10308-account-deprovisioning";
    FeatureFlag["VerifiedSsoDomainEndpoint"] = "pm-12337-refactor-sso-details-endpoint";
    FeatureFlag["LimitItemDeletion"] = "pm-15493-restrict-item-deletion-to-can-manage-permission";
    /* Autofill */
    FeatureFlag["BlockBrowserInjectionsByDomain"] = "block-browser-injections-by-domain";
    FeatureFlag["DelayFido2PageScriptInitWithinMv2"] = "delay-fido2-page-script-init-within-mv2";
    FeatureFlag["EnableNewCardCombinedExpiryAutofill"] = "enable-new-card-combined-expiry-autofill";
    FeatureFlag["GenerateIdentityFillScriptRefactor"] = "generate-identity-fill-script-refactor";
    FeatureFlag["IdpAutoSubmitLogin"] = "idp-auto-submit-login";
    FeatureFlag["InlineMenuFieldQualification"] = "inline-menu-field-qualification";
    FeatureFlag["InlineMenuPositioningImprovements"] = "inline-menu-positioning-improvements";
    FeatureFlag["NotificationBarAddLoginImprovements"] = "notification-bar-add-login-improvements";
    FeatureFlag["NotificationRefresh"] = "notification-refresh";
    FeatureFlag["UseTreeWalkerApiForPageDetailsCollection"] = "use-tree-walker-api-for-page-details-collection";
    /* Tools */
    FeatureFlag["ItemShare"] = "item-share";
    FeatureFlag["CriticalApps"] = "pm-14466-risk-insights-critical-application";
    FeatureFlag["EnableRiskInsightsNotifications"] = "enable-risk-insights-notifications";
    FeatureFlag["DesktopSendUIRefresh"] = "desktop-send-ui-refresh";
    FeatureFlag["ExportAttachments"] = "export-attachments";
    /* Vault */
    FeatureFlag["PM8851_BrowserOnboardingNudge"] = "pm-8851-browser-onboarding-nudge";
    FeatureFlag["PM9111ExtensionPersistAddEditForm"] = "pm-9111-extension-persist-add-edit-form";
    FeatureFlag["NewDeviceVerificationTemporaryDismiss"] = "new-device-temporary-dismiss";
    FeatureFlag["NewDeviceVerificationPermanentDismiss"] = "new-device-permanent-dismiss";
    FeatureFlag["VaultBulkManagementAction"] = "vault-bulk-management-action";
    FeatureFlag["SecurityTasks"] = "security-tasks";
    /* Auth */
    FeatureFlag["PM9112_DeviceApprovalPersistence"] = "pm-9112-device-approval-persistence";
    FeatureFlag["PM4154_BulkEncryptionService"] = "PM-4154-bulk-encryption-service";
    FeatureFlag["UnauthenticatedExtensionUIRefresh"] = "unauth-ui-refresh";
    FeatureFlag["CipherKeyEncryption"] = "cipher-key-encryption";
    FeatureFlag["TrialPaymentOptional"] = "PM-8163-trial-payment";
    FeatureFlag["MacOsNativeCredentialSync"] = "macos-native-credential-sync";
    FeatureFlag["PrivateKeyRegeneration"] = "pm-12241-private-key-regeneration";
    FeatureFlag["ResellerManagedOrgAlert"] = "PM-15814-alert-owners-of-reseller-managed-orgs";
    FeatureFlag["AccountDeprovisioningBanner"] = "pm-17120-account-deprovisioning-admin-console-banner";
    FeatureFlag["PM15179_AddExistingOrgsFromProviderPortal"] = "pm-15179-add-existing-orgs-from-provider-portal";
    FeatureFlag["PM12276_BreadcrumbEventLogs"] = "pm-12276-breadcrumbing-for-business-features";
    FeatureFlag["PM18794_ProviderPaymentMethod"] = "pm-18794-provider-payment-method";
})(bw_feature_flag_enum_FeatureFlag || (bw_feature_flag_enum_FeatureFlag = {}));
// Helper to ensure the value is treated as a boolean.
const bw_FALSE = false;
/**
 * Default value for feature flags.
 *
 * DO NOT enable previously disabled flags, REMOVE them instead.
 * We support true as a value as we prefer flags to "enable" not "disable".
 */
const bw_DefaultFeatureFlagValue = {
    /* Admin Console Team */
    [bw_feature_flag_enum_FeatureFlag.AccountDeprovisioning]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.VerifiedSsoDomainEndpoint]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.LimitItemDeletion]: bw_FALSE,
    /* Autofill */
    [bw_feature_flag_enum_FeatureFlag.BlockBrowserInjectionsByDomain]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.DelayFido2PageScriptInitWithinMv2]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.EnableNewCardCombinedExpiryAutofill]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.GenerateIdentityFillScriptRefactor]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.IdpAutoSubmitLogin]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.InlineMenuFieldQualification]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.InlineMenuPositioningImprovements]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.NotificationBarAddLoginImprovements]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.NotificationRefresh]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.UseTreeWalkerApiForPageDetailsCollection]: bw_FALSE,
    /* Tools */
    [bw_feature_flag_enum_FeatureFlag.ItemShare]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.CriticalApps]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.EnableRiskInsightsNotifications]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.DesktopSendUIRefresh]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.ExportAttachments]: bw_FALSE,
    /* Vault */
    [bw_feature_flag_enum_FeatureFlag.PM8851_BrowserOnboardingNudge]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.PM9111ExtensionPersistAddEditForm]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.NewDeviceVerificationTemporaryDismiss]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.NewDeviceVerificationPermanentDismiss]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.VaultBulkManagementAction]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.SecurityTasks]: bw_FALSE,
    /* Auth */
    [bw_feature_flag_enum_FeatureFlag.PM9112_DeviceApprovalPersistence]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.PM4154_BulkEncryptionService]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.UnauthenticatedExtensionUIRefresh]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.CipherKeyEncryption]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.TrialPaymentOptional]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.MacOsNativeCredentialSync]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.PrivateKeyRegeneration]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.ResellerManagedOrgAlert]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.AccountDeprovisioningBanner]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.PM15179_AddExistingOrgsFromProviderPortal]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.PM12276_BreadcrumbEventLogs]: bw_FALSE,
    [bw_feature_flag_enum_FeatureFlag.PM18794_ProviderPaymentMethod]: bw_FALSE,
};

;// ../../libs/key-management/src/user-asymmetric-key-regeneration/services/default-user-asymmetric-key-regeneration.service.ts
var bw_default_user_asymmetric_key_regeneration_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_DefaultUserAsymmetricKeysRegenerationService {
    constructor(keyService, cipherService, userAsymmetricKeysRegenerationApiService, logService, sdkService, apiService, configService) {
        this.keyService = keyService;
        this.cipherService = cipherService;
        this.userAsymmetricKeysRegenerationApiService = userAsymmetricKeysRegenerationApiService;
        this.logService = logService;
        this.sdkService = sdkService;
        this.apiService = apiService;
        this.configService = configService;
    }
    regenerateIfNeeded(userId) {
        return bw_default_user_asymmetric_key_regeneration_service_awaiter(this, void 0, void 0, function* () {
            try {
                const privateKeyRegenerationFlag = yield this.configService.getFeatureFlag(FeatureFlag.PrivateKeyRegeneration);
                if (privateKeyRegenerationFlag) {
                    const shouldRegenerate = yield this.shouldRegenerate(userId);
                    if (shouldRegenerate) {
                        yield this.regenerateUserAsymmetricKeys(userId);
                    }
                }
            }
            catch (error) {
                this.logService.error("[UserAsymmetricKeyRegeneration] An error occurred: " +
                    error +
                    " Skipping regeneration for the user.");
            }
        });
    }
    shouldRegenerate(userId) {
        return bw_default_user_asymmetric_key_regeneration_service_awaiter(this, void 0, void 0, function* () {
            const userKey = yield firstValueFrom(this.keyService.userKey$(userId));
            // For SSO logins from untrusted devices, the userKey will not be available, and the private key regeneration process should be skipped.
            // In such cases, regeneration will occur on the following device login flow.
            if (!userKey) {
                this.logService.info("[UserAsymmetricKeyRegeneration] User symmetric key unavailable, skipping regeneration for the user.");
                return false;
            }
            const [userKeyEncryptedPrivateKey, publicKeyResponse] = yield firstValueFrom(combineLatest([
                this.keyService.userEncryptedPrivateKey$(userId),
                this.apiService.getUserPublicKey(userId),
            ]));
            if (!userKeyEncryptedPrivateKey || !publicKeyResponse) {
                this.logService.warning("[UserAsymmetricKeyRegeneration] User's asymmetric key initialization data is unavailable, skipping regeneration.");
                return false;
            }
            const verificationResponse = yield firstValueFrom(this.sdkService.client$.pipe(map((sdk) => {
                if (sdk === undefined) {
                    throw new Error("SDK is undefined");
                }
                return sdk.crypto().verify_asymmetric_keys({
                    userKey: userKey.keyB64,
                    userPublicKey: publicKeyResponse.publicKey,
                    userKeyEncryptedPrivateKey: userKeyEncryptedPrivateKey,
                });
            })));
            if (verificationResponse.privateKeyDecryptable) {
                if (verificationResponse.validPrivateKey) {
                    // The private key is decryptable and valid. Should not regenerate.
                    return false;
                }
                else {
                    // The private key is decryptable but not valid so we should regenerate it.
                    this.logService.info("[UserAsymmetricKeyRegeneration] User's private key is decryptable but not a valid key, attempting regeneration.");
                    return true;
                }
            }
            // The private isn't decryptable, check to see if we can decrypt something with the userKey.
            const userKeyCanDecrypt = yield this.userKeyCanDecrypt(userKey, userId);
            if (userKeyCanDecrypt) {
                this.logService.info("[UserAsymmetricKeyRegeneration] User Asymmetric Key decryption failure detected, attempting regeneration.");
                return true;
            }
            this.logService.warning("[UserAsymmetricKeyRegeneration] User Asymmetric Key decryption failure detected, but unable to determine User Symmetric Key validity, skipping regeneration.");
            return false;
        });
    }
    regenerateUserAsymmetricKeys(userId) {
        return bw_default_user_asymmetric_key_regeneration_service_awaiter(this, void 0, void 0, function* () {
            const userKey = yield firstValueFrom(this.keyService.userKey$(userId));
            if (userKey == null) {
                throw new Error("User key not found");
            }
            const makeKeyPairResponse = yield firstValueFrom(this.sdkService.client$.pipe(map((sdk) => {
                if (sdk === undefined) {
                    throw new Error("SDK is undefined");
                }
                return sdk.crypto().make_key_pair(userKey.keyB64);
            })));
            try {
                yield this.userAsymmetricKeysRegenerationApiService.regenerateUserAsymmetricKeys(makeKeyPairResponse.userPublicKey, new EncString(makeKeyPairResponse.userKeyEncryptedPrivateKey));
            }
            catch (error) {
                if ((error === null || error === void 0 ? void 0 : error.message) === "Key regeneration not supported for this user.") {
                    this.logService.info("[UserAsymmetricKeyRegeneration] Regeneration not supported for this user at this time.");
                }
                else {
                    this.logService.error("[UserAsymmetricKeyRegeneration] Regeneration error when submitting the request to the server: " +
                        error);
                }
                return;
            }
            yield this.keyService.setPrivateKey(makeKeyPairResponse.userKeyEncryptedPrivateKey, userId);
            this.logService.info("[UserAsymmetricKeyRegeneration] User's asymmetric keys successfully regenerated.");
        });
    }
    userKeyCanDecrypt(userKey, userId) {
        return bw_default_user_asymmetric_key_regeneration_service_awaiter(this, void 0, void 0, function* () {
            const ciphers = yield this.cipherService.getAll(userId);
            const cipher = ciphers.find((cipher) => cipher.organizationId == null);
            if (cipher != null) {
                try {
                    yield cipher.decrypt(userKey);
                    return true;
                }
                catch (error) {
                    this.logService.error("[UserAsymmetricKeyRegeneration] User Symmetric Key validation error: " + error);
                    return false;
                }
            }
            return false;
        });
    }
}

;// ../../libs/key-management/src/user-asymmetric-key-regeneration/services/default-user-asymmetric-key-regeneration-api.service.ts
var bw_default_user_asymmetric_key_regeneration_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_DefaultUserAsymmetricKeysRegenerationApiService {
    constructor(apiService) {
        this.apiService = apiService;
    }
    regenerateUserAsymmetricKeys(userPublicKey, userKeyEncryptedUserPrivateKey) {
        return bw_default_user_asymmetric_key_regeneration_api_service_awaiter(this, void 0, void 0, function* () {
            const request = {
                userPublicKey,
                userKeyEncryptedUserPrivateKey,
            };
            yield this.apiService.send("POST", "/accounts/key-management/regenerate-keys", request, true, true);
        });
    }
}

;// ../../libs/key-management/src/user-asymmetric-key-regeneration/index.ts





;// ../../libs/key-management/src/index.ts













;// ../../libs/common/src/auth/models/request/identity-token/device.request.ts
class bw_DeviceRequest {
    constructor(appId, platformUtilsService) {
        this.type = platformUtilsService.getDevice();
        this.name = platformUtilsService.getDeviceString();
        this.identifier = appId;
        this.pushToken = null;
    }
    static fromJSON(json) {
        return Object.assign(Object.create(bw_DeviceRequest.prototype), json);
    }
}

;// ../../libs/common/src/auth/models/request/identity-token/token.request.ts
class bw_TokenRequest {
    constructor(twoFactor, device) {
        this.twoFactor = twoFactor;
        this.device = device != null ? device : null;
    }
    alterIdentityTokenHeaders(headers) {
        // Implemented in subclass if required
    }
    setTwoFactor(twoFactor) {
        this.twoFactor = twoFactor;
    }
    setAuthRequestAccessCode(accessCode) {
        this.authRequest = accessCode;
    }
    toIdentityToken(clientId) {
        const obj = {
            scope: "api offline_access",
            client_id: clientId,
        };
        if (this.device) {
            obj.deviceType = this.device.type;
            obj.deviceIdentifier = this.device.identifier;
            obj.deviceName = this.device.name;
            // no push tokens for browser apps yet
            // obj.devicePushToken = this.device.pushToken;
        }
        //passswordless login
        if (this.authRequest) {
            obj.authRequest = this.authRequest;
        }
        if (this.twoFactor) {
            if (this.twoFactor.token && this.twoFactor.provider != null) {
                obj.twoFactorToken = this.twoFactor.token;
                obj.twoFactorProvider = this.twoFactor.provider;
                obj.twoFactorRemember = this.twoFactor.remember ? "1" : "0";
            }
        }
        return obj;
    }
}

;// ../../libs/common/src/auth/models/request/identity-token/password-token.request.ts




class bw_PasswordTokenRequest extends bw_TokenRequest {
    constructor(email, masterPasswordHash, captchaResponse, twoFactor, device, newDeviceOtp) {
        super(twoFactor, device);
        this.email = email;
        this.masterPasswordHash = masterPasswordHash;
        this.captchaResponse = captchaResponse;
        this.twoFactor = twoFactor;
        this.newDeviceOtp = newDeviceOtp;
    }
    toIdentityToken(clientId) {
        const obj = super.toIdentityToken(clientId);
        obj.grant_type = "password";
        obj.username = this.email;
        obj.password = this.masterPasswordHash;
        if (this.captchaResponse != null) {
            obj.captchaResponse = this.captchaResponse;
        }
        if (this.newDeviceOtp) {
            obj.newDeviceOtp = this.newDeviceOtp;
        }
        return obj;
    }
    alterIdentityTokenHeaders(headers) {
        headers.set("Auth-Email", bw_utils_Utils.fromUtf8ToUrlB64(this.email));
    }
    static fromJSON(json) {
        return Object.assign(Object.create(bw_PasswordTokenRequest.prototype), json, {
            device: json.device ? bw_DeviceRequest.fromJSON(json.device) : undefined,
            twoFactor: json.twoFactor
                ? Object.assign(new bw_TokenTwoFactorRequest(), json.twoFactor)
                : undefined,
        });
    }
}

;// ../../libs/common/src/auth/enums/two-factor-provider-type.ts
var bw_TwoFactorProviderType;
(function (TwoFactorProviderType) {
    TwoFactorProviderType[TwoFactorProviderType["Authenticator"] = 0] = "Authenticator";
    TwoFactorProviderType[TwoFactorProviderType["Email"] = 1] = "Email";
    TwoFactorProviderType[TwoFactorProviderType["Duo"] = 2] = "Duo";
    TwoFactorProviderType[TwoFactorProviderType["Yubikey"] = 3] = "Yubikey";
    TwoFactorProviderType[TwoFactorProviderType["U2f"] = 4] = "U2f";
    TwoFactorProviderType[TwoFactorProviderType["Remember"] = 5] = "Remember";
    TwoFactorProviderType[TwoFactorProviderType["OrganizationDuo"] = 6] = "OrganizationDuo";
    TwoFactorProviderType[TwoFactorProviderType["WebAuthn"] = 7] = "WebAuthn";
    TwoFactorProviderType[TwoFactorProviderType["RecoveryCode"] = 8] = "RecoveryCode";
})(bw_TwoFactorProviderType || (bw_TwoFactorProviderType = {}));

;// ../../libs/common/src/auth/models/domain/force-set-password-reason.ts
/*
 * This enum is used to determine if a user should be forced to initially set or reset their password
 * on login (server flag) or unlock via MP (client evaluation).
 */
var bw_ForceSetPasswordReason;
(function (ForceSetPasswordReason) {
    /**
     * A password reset should not be forced.
     */
    ForceSetPasswordReason[ForceSetPasswordReason["None"] = 0] = "None";
    /**
     * Occurs when an organization admin forces a user to reset their password.
     * Communicated via server flag.
     */
    ForceSetPasswordReason[ForceSetPasswordReason["AdminForcePasswordReset"] = 1] = "AdminForcePasswordReset";
    /**
     * Occurs when a user logs in / unlocks their vault with a master password that does not meet an organization's
     * master password policy that is enforced on login/unlock.
     * Only set client side b/c server can't evaluate MP.
     */
    ForceSetPasswordReason[ForceSetPasswordReason["WeakMasterPassword"] = 2] = "WeakMasterPassword";
    /**
     * Occurs when a TDE user without a password obtains the password reset permission.
     * Set post login & decryption client side and by server in sync (to catch logged in users).
     */
    ForceSetPasswordReason[ForceSetPasswordReason["TdeUserWithoutPasswordHasPasswordResetPermission"] = 3] = "TdeUserWithoutPasswordHasPasswordResetPermission";
    /**
     * Occurs when TDE is disabled and master password has to be set.
     */
    ForceSetPasswordReason[ForceSetPasswordReason["TdeOffboarding"] = 4] = "TdeOffboarding";
})(bw_ForceSetPasswordReason || (bw_ForceSetPasswordReason = {}));

;// ../../libs/common/src/auth/models/domain/auth-result.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_AuthResult {
    constructor() {
        this.captchaSiteKey = "";
        // TODO: PM-3287 - Remove this after 3 releases of backwards compatibility. - Target release 2023.12 for removal
        /**
         * @deprecated
         * Replace with using UserDecryptionOptions to determine if the user does
         * not have a master password and is not using Key Connector.
         * */
        this.resetMasterPassword = false;
        this.forcePasswordReset = bw_ForceSetPasswordReason.None;
        this.twoFactorProviders = null;
    }
    get requiresCaptcha() {
        return !bw_utils_Utils.isNullOrWhitespace(this.captchaSiteKey);
    }
    get requiresTwoFactor() {
        return this.twoFactorProviders != null;
    }
}

;// ../../libs/common/src/auth/models/response/identity-captcha.response.ts

class bw_IdentityCaptchaResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.siteKey = this.getResponseProperty("HCaptcha_SiteKey");
    }
}

;// ../../libs/common/src/auth/models/response/identity-device-verification.response.ts

class bw_IdentityDeviceVerificationResponse extends bw_BaseResponse {
    constructor(response) {
        var _a;
        super(response);
        this.deviceVerified = (_a = this.getResponseProperty("DeviceVerified")) !== null && _a !== void 0 ? _a : false;
        this.captchaToken = this.getResponseProperty("CaptchaBypassToken");
    }
}

;// ../../libs/common/src/auth/models/response/master-password-policy.response.ts

class bw_MasterPasswordPolicyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.minComplexity = this.getResponseProperty("MinComplexity");
        this.minLength = this.getResponseProperty("MinLength");
        this.requireUpper = this.getResponseProperty("RequireUpper");
        this.requireLower = this.getResponseProperty("RequireLower");
        this.requireNumbers = this.getResponseProperty("RequireNumbers");
        this.requireSpecial = this.getResponseProperty("RequireSpecial");
        this.enforceOnLogin = this.getResponseProperty("EnforceOnLogin");
    }
}

;// ../../libs/common/src/auth/models/response/user-decryption-options/key-connector-user-decryption-option.response.ts

class bw_KeyConnectorUserDecryptionOptionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.keyConnectorUrl = this.getResponseProperty("KeyConnectorUrl");
    }
}

;// ../../libs/common/src/auth/models/response/user-decryption-options/trusted-device-user-decryption-option.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_TrustedDeviceUserDecryptionOptionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.hasAdminApproval = this.getResponseProperty("HasAdminApproval");
        this.hasLoginApprovingDevice = this.getResponseProperty("HasLoginApprovingDevice");
        this.hasManageResetPasswordPermission = this.getResponseProperty("HasManageResetPasswordPermission");
        this.isTdeOffboarding = this.getResponseProperty("IsTdeOffboarding");
        if (response.EncryptedPrivateKey) {
            this.encryptedPrivateKey = new bw_enc_string_EncString(this.getResponseProperty("EncryptedPrivateKey"));
        }
        if (response.EncryptedUserKey) {
            this.encryptedUserKey = new bw_enc_string_EncString(this.getResponseProperty("EncryptedUserKey"));
        }
    }
}

;// ../../libs/common/src/auth/models/response/user-decryption-options/webauthn-prf-decryption-option.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_WebAuthnPrfDecryptionOptionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        if (response.EncryptedPrivateKey) {
            this.encryptedPrivateKey = new bw_enc_string_EncString(this.getResponseProperty("EncryptedPrivateKey"));
        }
        if (response.EncryptedUserKey) {
            this.encryptedUserKey = new bw_enc_string_EncString(this.getResponseProperty("EncryptedUserKey"));
        }
    }
}

;// ../../libs/common/src/auth/models/response/user-decryption-options/user-decryption-options.response.ts




class bw_UserDecryptionOptionsResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.hasMasterPassword = this.getResponseProperty("HasMasterPassword");
        if (response.TrustedDeviceOption) {
            this.trustedDeviceOption = new bw_TrustedDeviceUserDecryptionOptionResponse(this.getResponseProperty("TrustedDeviceOption"));
        }
        if (response.KeyConnectorOption) {
            this.keyConnectorOption = new bw_KeyConnectorUserDecryptionOptionResponse(this.getResponseProperty("KeyConnectorOption"));
        }
        if (response.WebAuthnPrfOption) {
            this.webAuthnPrfOption = new bw_WebAuthnPrfDecryptionOptionResponse(this.getResponseProperty("WebAuthnPrfOption"));
        }
    }
}

;// ../../libs/common/src/auth/models/response/identity-token.response.ts



class bw_IdentityTokenResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.accessToken = response.access_token;
        this.expiresIn = response.expires_in;
        this.refreshToken = response.refresh_token;
        this.tokenType = response.token_type;
        this.resetMasterPassword = this.getResponseProperty("ResetMasterPassword");
        this.privateKey = this.getResponseProperty("PrivateKey");
        this.key = this.getResponseProperty("Key");
        this.twoFactorToken = this.getResponseProperty("TwoFactorToken");
        this.kdf = this.getResponseProperty("Kdf");
        this.kdfIterations = this.getResponseProperty("KdfIterations");
        this.kdfMemory = this.getResponseProperty("KdfMemory");
        this.kdfParallelism = this.getResponseProperty("KdfParallelism");
        this.forcePasswordReset = this.getResponseProperty("ForcePasswordReset");
        this.apiUseKeyConnector = this.getResponseProperty("ApiUseKeyConnector");
        this.keyConnectorUrl = this.getResponseProperty("KeyConnectorUrl");
        this.masterPasswordPolicy = new bw_MasterPasswordPolicyResponse(this.getResponseProperty("MasterPasswordPolicy"));
        if (response.UserDecryptionOptions) {
            this.userDecryptionOptions = new bw_UserDecryptionOptionsResponse(this.getResponseProperty("UserDecryptionOptions"));
        }
    }
}

;// ../../libs/common/src/auth/models/response/identity-two-factor.response.ts


class bw_IdentityTwoFactorResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.captchaToken = this.getResponseProperty("CaptchaBypassToken");
        this.twoFactorProviders = this.getResponseProperty("TwoFactorProviders");
        this.twoFactorProviders2 = this.getResponseProperty("TwoFactorProviders2");
        this.masterPasswordPolicy = new bw_MasterPasswordPolicyResponse(this.getResponseProperty("MasterPasswordPolicy"));
        this.ssoEmail2faSessionToken = this.getResponseProperty("SsoEmail2faSessionToken");
        this.email = this.getResponseProperty("Email");
    }
}

;// ../../libs/common/src/enums/client-type.enum.ts
var bw_ClientType;
(function (ClientType) {
    ClientType["Web"] = "web";
    ClientType["Browser"] = "browser";
    ClientType["Desktop"] = "desktop";
    // Mobile = "mobile",
    ClientType["Cli"] = "cli";
    // DirectoryConnector = "connector",
})(bw_ClientType || (bw_ClientType = {}));

;// ../../libs/common/src/enums/device-type.enum.ts
var bw_DeviceType;
(function (DeviceType) {
    DeviceType[DeviceType["Android"] = 0] = "Android";
    DeviceType[DeviceType["iOS"] = 1] = "iOS";
    DeviceType[DeviceType["ChromeExtension"] = 2] = "ChromeExtension";
    DeviceType[DeviceType["FirefoxExtension"] = 3] = "FirefoxExtension";
    DeviceType[DeviceType["OperaExtension"] = 4] = "OperaExtension";
    DeviceType[DeviceType["EdgeExtension"] = 5] = "EdgeExtension";
    DeviceType[DeviceType["WindowsDesktop"] = 6] = "WindowsDesktop";
    DeviceType[DeviceType["MacOsDesktop"] = 7] = "MacOsDesktop";
    DeviceType[DeviceType["LinuxDesktop"] = 8] = "LinuxDesktop";
    DeviceType[DeviceType["ChromeBrowser"] = 9] = "ChromeBrowser";
    DeviceType[DeviceType["FirefoxBrowser"] = 10] = "FirefoxBrowser";
    DeviceType[DeviceType["OperaBrowser"] = 11] = "OperaBrowser";
    DeviceType[DeviceType["EdgeBrowser"] = 12] = "EdgeBrowser";
    DeviceType[DeviceType["IEBrowser"] = 13] = "IEBrowser";
    DeviceType[DeviceType["UnknownBrowser"] = 14] = "UnknownBrowser";
    DeviceType[DeviceType["AndroidAmazon"] = 15] = "AndroidAmazon";
    DeviceType[DeviceType["UWP"] = 16] = "UWP";
    DeviceType[DeviceType["SafariBrowser"] = 17] = "SafariBrowser";
    DeviceType[DeviceType["VivaldiBrowser"] = 18] = "VivaldiBrowser";
    DeviceType[DeviceType["VivaldiExtension"] = 19] = "VivaldiExtension";
    DeviceType[DeviceType["SafariExtension"] = 20] = "SafariExtension";
    DeviceType[DeviceType["SDK"] = 21] = "SDK";
    DeviceType[DeviceType["Server"] = 22] = "Server";
    DeviceType[DeviceType["WindowsCLI"] = 23] = "WindowsCLI";
    DeviceType[DeviceType["MacOsCLI"] = 24] = "MacOsCLI";
    DeviceType[DeviceType["LinuxCLI"] = 25] = "LinuxCLI";
})(bw_DeviceType || (bw_DeviceType = {}));
const bw_DeviceTypeMetadata = {
    [bw_DeviceType.Android]: { category: "mobile", platform: "Android" },
    [bw_DeviceType.iOS]: { category: "mobile", platform: "iOS" },
    [bw_DeviceType.AndroidAmazon]: { category: "mobile", platform: "Amazon" },
    [bw_DeviceType.ChromeExtension]: { category: "extension", platform: "Chrome" },
    [bw_DeviceType.FirefoxExtension]: { category: "extension", platform: "Firefox" },
    [bw_DeviceType.OperaExtension]: { category: "extension", platform: "Opera" },
    [bw_DeviceType.EdgeExtension]: { category: "extension", platform: "Edge" },
    [bw_DeviceType.VivaldiExtension]: { category: "extension", platform: "Vivaldi" },
    [bw_DeviceType.SafariExtension]: { category: "extension", platform: "Safari" },
    [bw_DeviceType.ChromeBrowser]: { category: "webVault", platform: "Chrome" },
    [bw_DeviceType.FirefoxBrowser]: { category: "webVault", platform: "Firefox" },
    [bw_DeviceType.OperaBrowser]: { category: "webVault", platform: "Opera" },
    [bw_DeviceType.EdgeBrowser]: { category: "webVault", platform: "Edge" },
    [bw_DeviceType.IEBrowser]: { category: "webVault", platform: "IE" },
    [bw_DeviceType.SafariBrowser]: { category: "webVault", platform: "Safari" },
    [bw_DeviceType.VivaldiBrowser]: { category: "webVault", platform: "Vivaldi" },
    [bw_DeviceType.UnknownBrowser]: { category: "webVault", platform: "Unknown" },
    [bw_DeviceType.WindowsDesktop]: { category: "desktop", platform: "Windows" },
    [bw_DeviceType.MacOsDesktop]: { category: "desktop", platform: "macOS" },
    [bw_DeviceType.LinuxDesktop]: { category: "desktop", platform: "Linux" },
    [bw_DeviceType.UWP]: { category: "desktop", platform: "Windows UWP" },
    [bw_DeviceType.WindowsCLI]: { category: "cli", platform: "Windows" },
    [bw_DeviceType.MacOsCLI]: { category: "cli", platform: "macOS" },
    [bw_DeviceType.LinuxCLI]: { category: "cli", platform: "Linux" },
    [bw_DeviceType.SDK]: { category: "sdk", platform: "" },
    [bw_DeviceType.Server]: { category: "server", platform: "" },
};

;// ../../libs/common/src/enums/event-system-user.enum.ts
// Note: the enum key is used to describe the EventSystemUser in the UI. Be careful about changing it.
var bw_EventSystemUser;
(function (EventSystemUser) {
    EventSystemUser[EventSystemUser["SCIM"] = 1] = "SCIM";
    EventSystemUser[EventSystemUser["DomainVerification"] = 2] = "DomainVerification";
    EventSystemUser[EventSystemUser["PublicApi"] = 3] = "PublicApi";
})(bw_EventSystemUser || (bw_EventSystemUser = {}));

;// ../../libs/common/src/enums/event-type.enum.ts
// Increment by 100 for each new set of events
var bw_EventType;
(function (EventType) {
    EventType[EventType["User_LoggedIn"] = 1000] = "User_LoggedIn";
    EventType[EventType["User_ChangedPassword"] = 1001] = "User_ChangedPassword";
    EventType[EventType["User_Updated2fa"] = 1002] = "User_Updated2fa";
    EventType[EventType["User_Disabled2fa"] = 1003] = "User_Disabled2fa";
    EventType[EventType["User_Recovered2fa"] = 1004] = "User_Recovered2fa";
    EventType[EventType["User_FailedLogIn"] = 1005] = "User_FailedLogIn";
    EventType[EventType["User_FailedLogIn2fa"] = 1006] = "User_FailedLogIn2fa";
    EventType[EventType["User_ClientExportedVault"] = 1007] = "User_ClientExportedVault";
    EventType[EventType["User_UpdatedTempPassword"] = 1008] = "User_UpdatedTempPassword";
    EventType[EventType["User_MigratedKeyToKeyConnector"] = 1009] = "User_MigratedKeyToKeyConnector";
    EventType[EventType["User_RequestedDeviceApproval"] = 1010] = "User_RequestedDeviceApproval";
    EventType[EventType["User_TdeOffboardingPasswordSet"] = 1011] = "User_TdeOffboardingPasswordSet";
    EventType[EventType["Cipher_Created"] = 1100] = "Cipher_Created";
    EventType[EventType["Cipher_Updated"] = 1101] = "Cipher_Updated";
    EventType[EventType["Cipher_Deleted"] = 1102] = "Cipher_Deleted";
    EventType[EventType["Cipher_AttachmentCreated"] = 1103] = "Cipher_AttachmentCreated";
    EventType[EventType["Cipher_AttachmentDeleted"] = 1104] = "Cipher_AttachmentDeleted";
    EventType[EventType["Cipher_Shared"] = 1105] = "Cipher_Shared";
    EventType[EventType["Cipher_UpdatedCollections"] = 1106] = "Cipher_UpdatedCollections";
    EventType[EventType["Cipher_ClientViewed"] = 1107] = "Cipher_ClientViewed";
    EventType[EventType["Cipher_ClientToggledPasswordVisible"] = 1108] = "Cipher_ClientToggledPasswordVisible";
    EventType[EventType["Cipher_ClientToggledHiddenFieldVisible"] = 1109] = "Cipher_ClientToggledHiddenFieldVisible";
    EventType[EventType["Cipher_ClientToggledCardCodeVisible"] = 1110] = "Cipher_ClientToggledCardCodeVisible";
    EventType[EventType["Cipher_ClientCopiedPassword"] = 1111] = "Cipher_ClientCopiedPassword";
    EventType[EventType["Cipher_ClientCopiedHiddenField"] = 1112] = "Cipher_ClientCopiedHiddenField";
    EventType[EventType["Cipher_ClientCopiedCardCode"] = 1113] = "Cipher_ClientCopiedCardCode";
    EventType[EventType["Cipher_ClientAutofilled"] = 1114] = "Cipher_ClientAutofilled";
    EventType[EventType["Cipher_SoftDeleted"] = 1115] = "Cipher_SoftDeleted";
    EventType[EventType["Cipher_Restored"] = 1116] = "Cipher_Restored";
    EventType[EventType["Cipher_ClientToggledCardNumberVisible"] = 1117] = "Cipher_ClientToggledCardNumberVisible";
    EventType[EventType["Cipher_ClientToggledTOTPSeedVisible"] = 1118] = "Cipher_ClientToggledTOTPSeedVisible";
    EventType[EventType["Collection_Created"] = 1300] = "Collection_Created";
    EventType[EventType["Collection_Updated"] = 1301] = "Collection_Updated";
    EventType[EventType["Collection_Deleted"] = 1302] = "Collection_Deleted";
    EventType[EventType["Group_Created"] = 1400] = "Group_Created";
    EventType[EventType["Group_Updated"] = 1401] = "Group_Updated";
    EventType[EventType["Group_Deleted"] = 1402] = "Group_Deleted";
    EventType[EventType["OrganizationUser_Invited"] = 1500] = "OrganizationUser_Invited";
    EventType[EventType["OrganizationUser_Confirmed"] = 1501] = "OrganizationUser_Confirmed";
    EventType[EventType["OrganizationUser_Updated"] = 1502] = "OrganizationUser_Updated";
    EventType[EventType["OrganizationUser_Removed"] = 1503] = "OrganizationUser_Removed";
    EventType[EventType["OrganizationUser_UpdatedGroups"] = 1504] = "OrganizationUser_UpdatedGroups";
    EventType[EventType["OrganizationUser_UnlinkedSso"] = 1505] = "OrganizationUser_UnlinkedSso";
    EventType[EventType["OrganizationUser_ResetPassword_Enroll"] = 1506] = "OrganizationUser_ResetPassword_Enroll";
    EventType[EventType["OrganizationUser_ResetPassword_Withdraw"] = 1507] = "OrganizationUser_ResetPassword_Withdraw";
    EventType[EventType["OrganizationUser_AdminResetPassword"] = 1508] = "OrganizationUser_AdminResetPassword";
    EventType[EventType["OrganizationUser_ResetSsoLink"] = 1509] = "OrganizationUser_ResetSsoLink";
    EventType[EventType["OrganizationUser_FirstSsoLogin"] = 1510] = "OrganizationUser_FirstSsoLogin";
    EventType[EventType["OrganizationUser_Revoked"] = 1511] = "OrganizationUser_Revoked";
    EventType[EventType["OrganizationUser_Restored"] = 1512] = "OrganizationUser_Restored";
    EventType[EventType["OrganizationUser_ApprovedAuthRequest"] = 1513] = "OrganizationUser_ApprovedAuthRequest";
    EventType[EventType["OrganizationUser_RejectedAuthRequest"] = 1514] = "OrganizationUser_RejectedAuthRequest";
    EventType[EventType["OrganizationUser_Deleted"] = 1515] = "OrganizationUser_Deleted";
    EventType[EventType["OrganizationUser_Left"] = 1516] = "OrganizationUser_Left";
    EventType[EventType["Organization_Updated"] = 1600] = "Organization_Updated";
    EventType[EventType["Organization_PurgedVault"] = 1601] = "Organization_PurgedVault";
    EventType[EventType["Organization_ClientExportedVault"] = 1602] = "Organization_ClientExportedVault";
    EventType[EventType["Organization_VaultAccessed"] = 1603] = "Organization_VaultAccessed";
    EventType[EventType["Organization_EnabledSso"] = 1604] = "Organization_EnabledSso";
    EventType[EventType["Organization_DisabledSso"] = 1605] = "Organization_DisabledSso";
    EventType[EventType["Organization_EnabledKeyConnector"] = 1606] = "Organization_EnabledKeyConnector";
    EventType[EventType["Organization_DisabledKeyConnector"] = 1607] = "Organization_DisabledKeyConnector";
    EventType[EventType["Organization_SponsorshipsSynced"] = 1608] = "Organization_SponsorshipsSynced";
    EventType[EventType["Organization_CollectionManagementUpdated"] = 1609] = "Organization_CollectionManagementUpdated";
    EventType[EventType["Policy_Updated"] = 1700] = "Policy_Updated";
    EventType[EventType["ProviderUser_Invited"] = 1800] = "ProviderUser_Invited";
    EventType[EventType["ProviderUser_Confirmed"] = 1801] = "ProviderUser_Confirmed";
    EventType[EventType["ProviderUser_Updated"] = 1802] = "ProviderUser_Updated";
    EventType[EventType["ProviderUser_Removed"] = 1803] = "ProviderUser_Removed";
    EventType[EventType["ProviderOrganization_Created"] = 1900] = "ProviderOrganization_Created";
    EventType[EventType["ProviderOrganization_Added"] = 1901] = "ProviderOrganization_Added";
    EventType[EventType["ProviderOrganization_Removed"] = 1902] = "ProviderOrganization_Removed";
    EventType[EventType["ProviderOrganization_VaultAccessed"] = 1903] = "ProviderOrganization_VaultAccessed";
    EventType[EventType["OrganizationDomain_Added"] = 2000] = "OrganizationDomain_Added";
    EventType[EventType["OrganizationDomain_Removed"] = 2001] = "OrganizationDomain_Removed";
    EventType[EventType["OrganizationDomain_Verified"] = 2002] = "OrganizationDomain_Verified";
    EventType[EventType["OrganizationDomain_NotVerified"] = 2003] = "OrganizationDomain_NotVerified";
    EventType[EventType["Secret_Retrieved"] = 2100] = "Secret_Retrieved";
})(bw_EventType || (bw_EventType = {}));

;// ../../libs/common/src/enums/http-status-code.enum.ts
/**
 * Hypertext Transfer Protocol (HTTP) response status codes.
 *
 * @see {@link https://en.wikipedia.org/wiki/List_of_HTTP_status_codes}
 * src: https://gist.github.com/RWOverdijk/6cef816cfdf5722228e01cc05fd4b094
 */
var bw_HttpStatusCode;
(function (HttpStatusCode) {
    /**
     * The server has received the request headers and the client should proceed to send the request body
     * (in the case of a request for which a body needs to be sent; for example, a POST request).
     * Sending a large request body to a server after a request has been rejected for inappropriate headers would be inefficient.
     * To have a server check the request's headers, a client must send Expect: 100-continue as a header in its initial request
     * and receive a 100 Continue status code in response before sending the body. The response 417 Expectation Failed indicates the request should not be continued.
     */
    HttpStatusCode[HttpStatusCode["Continue"] = 100] = "Continue";
    /**
     * The requester has asked the server to switch protocols and the server has agreed to do so.
     */
    HttpStatusCode[HttpStatusCode["SwitchingProtocols"] = 101] = "SwitchingProtocols";
    /**
     * A WebDAV request may contain many sub-requests involving file operations, requiring a long time to complete the request.
     * This code indicates that the server has received and is processing the request, but no response is available yet.
     * This prevents the client from timing out and assuming the request was lost.
     */
    HttpStatusCode[HttpStatusCode["Processing"] = 102] = "Processing";
    // **********************************************************************************************************
    // 200s - SUCCESS
    // **********************************************************************************************************
    /**
     * Standard response for successful HTTP requests.
     * The actual response will depend on the request method used.
     * In a GET request, the response will contain an entity corresponding to the requested resource.
     * In a POST request, the response will contain an entity describing or containing the result of the action.
     */
    HttpStatusCode[HttpStatusCode["Ok"] = 200] = "Ok";
    /**
     * The request has been fulfilled, resulting in the creation of a new resource.
     */
    HttpStatusCode[HttpStatusCode["Created"] = 201] = "Created";
    /**
     * The request has been accepted for processing, but the processing has not been completed.
     * The request might or might not be eventually acted upon, and may be disallowed when processing occurs.
     */
    HttpStatusCode[HttpStatusCode["Accepted"] = 202] = "Accepted";
    /**
     * SINCE HTTP/1.1
     * The server is a transforming proxy that received a 200 OK from its origin,
     * but is returning a modified version of the origin's response.
     */
    HttpStatusCode[HttpStatusCode["NonAuthoritativeInformation"] = 203] = "NonAuthoritativeInformation";
    /**
     * The server successfully processed the request and is not returning any content.
     */
    HttpStatusCode[HttpStatusCode["NoContent"] = 204] = "NoContent";
    /**
     * The server successfully processed the request, but is not returning any content.
     * Unlike a 204 response, this response requires that the requester reset the document view.
     */
    HttpStatusCode[HttpStatusCode["ResetContent"] = 205] = "ResetContent";
    /**
     * The server is delivering only part of the resource (byte serving) due to a range header sent by the client.
     * The range header is used by HTTP clients to enable resuming of interrupted downloads,
     * or split a download into multiple simultaneous streams.
     */
    HttpStatusCode[HttpStatusCode["PartialContent"] = 206] = "PartialContent";
    /**
     * The message body that follows is an XML message and can contain a number of separate response codes,
     * depending on how many sub-requests were made.
     */
    HttpStatusCode[HttpStatusCode["MultiStatus"] = 207] = "MultiStatus";
    /**
     * The members of a DAV binding have already been enumerated in a preceding part of the (multistatus) response,
     * and are not being included again.
     */
    HttpStatusCode[HttpStatusCode["AlreadyReported"] = 208] = "AlreadyReported";
    /**
     * The server has fulfilled a request for the resource,
     * and the response is a representation of the result of one or more instance-manipulations applied to the current instance.
     */
    HttpStatusCode[HttpStatusCode["ImUsed"] = 226] = "ImUsed";
    // **********************************************************************************************************
    // 300s - Redirections
    // **********************************************************************************************************
    /**
     * Indicates multiple options for the resource from which the client may choose (via agent-driven content negotiation).
     * For example, this code could be used to present multiple video format options,
     * to list files with different filename extensions, or to suggest word-sense disambiguation.
     */
    HttpStatusCode[HttpStatusCode["MultipleChoices"] = 300] = "MultipleChoices";
    /**
     * This and all future requests should be directed to the given URI.
     */
    HttpStatusCode[HttpStatusCode["MovedPermanently"] = 301] = "MovedPermanently";
    /**
     * This is an example of industry practice contradicting the standard.
     * The HTTP/1.0 specification (RFC 1945) required the client to perform a temporary redirect
     * (the original describing phrase was "Moved Temporarily"), but popular browsers implemented 302
     * with the functionality of a 303 See Other. Therefore, HTTP/1.1 added status codes 303 and 307
     * to distinguish between the two behaviours. However, some Web applications and frameworks
     * use the 302 status code as if it were the 303.
     */
    HttpStatusCode[HttpStatusCode["Found"] = 302] = "Found";
    /**
     * SINCE HTTP/1.1
     * The response to the request can be found under another URI using a GET method.
     * When received in response to a POST (or PUT/DELETE), the client should presume that
     * the server has received the data and should issue a redirect with a separate GET message.
     */
    HttpStatusCode[HttpStatusCode["SeeOther"] = 303] = "SeeOther";
    /**
     * Indicates that the resource has not been modified since the version specified by the request headers If-Modified-Since or If-None-Match.
     * In such case, there is no need to retransmit the resource since the client still has a previously-downloaded copy.
     */
    HttpStatusCode[HttpStatusCode["NotModified"] = 304] = "NotModified";
    /**
     * SINCE HTTP/1.1
     * The requested resource is available only through a proxy, the address for which is provided in the response.
     * Many HTTP clients (such as Mozilla and Internet Explorer) do not correctly handle responses with this status code, primarily for security reasons.
     */
    HttpStatusCode[HttpStatusCode["UseProxy"] = 305] = "UseProxy";
    /**
     * No longer used. Originally meant "Subsequent requests should use the specified proxy."
     */
    HttpStatusCode[HttpStatusCode["SwitchProxy"] = 306] = "SwitchProxy";
    /**
     * SINCE HTTP/1.1
     * In this case, the request should be repeated with another URI; however, future requests should still use the original URI.
     * In contrast to how 302 was historically implemented, the request method is not allowed to be changed when reissuing the original request.
     * For example, a POST request should be repeated using another POST request.
     */
    HttpStatusCode[HttpStatusCode["TemporaryRedirect"] = 307] = "TemporaryRedirect";
    /**
     * The request and all future requests should be repeated using another URI.
     * 307 and 308 parallel the behaviors of 302 and 301, but do not allow the HTTP method to change.
     * So, for example, submitting a form to a permanently redirected resource may continue smoothly.
     */
    HttpStatusCode[HttpStatusCode["PermanentRedirect"] = 308] = "PermanentRedirect";
    // **********************************************************************************************************
    // 400s - Client / User messed up
    // **********************************************************************************************************
    /**
     * The server cannot or will not process the request due to an apparent client error
     * (e.g., malformed request syntax, too large size, invalid request message framing, or deceptive request routing).
     */
    HttpStatusCode[HttpStatusCode["BadRequest"] = 400] = "BadRequest";
    /**
     * Similar to 403 Forbidden, but specifically for use when authentication is required and has failed or has not yet
     * been provided. The response must include a WWW-Authenticate header field containing a challenge applicable to the
     * requested resource. See Basic access authentication and Digest access authentication. 401 semantically means
     * "unauthenticated",i.e. the user does not have the necessary credentials.
     */
    HttpStatusCode[HttpStatusCode["Unauthorized"] = 401] = "Unauthorized";
    /**
     * Reserved for future use. The original intention was that this code might be used as part of some form of digital
     * cash or micro payment scheme, but that has not happened, and this code is not usually used.
     * Google Developers API uses this status if a particular developer has exceeded the daily limit on requests.
     */
    HttpStatusCode[HttpStatusCode["PaymentRequired"] = 402] = "PaymentRequired";
    /**
     * The request was valid, but the server is refusing action.
     * The user might not have the necessary permissions for a resource.
     */
    HttpStatusCode[HttpStatusCode["Forbidden"] = 403] = "Forbidden";
    /**
     * The requested resource could not be found but may be available in the future.
     * Subsequent requests by the client are permissible.
     */
    HttpStatusCode[HttpStatusCode["NotFound"] = 404] = "NotFound";
    /**
     * A request method is not supported for the requested resource;
     * for example, a GET request on a form that requires data to be presented via POST, or a PUT request on a read-only resource.
     */
    HttpStatusCode[HttpStatusCode["MethodNotAllowed"] = 405] = "MethodNotAllowed";
    /**
     * The requested resource is capable of generating only content not acceptable according to the Accept headers sent in the request.
     */
    HttpStatusCode[HttpStatusCode["NotAcceptable"] = 406] = "NotAcceptable";
    /**
     * The client must first authenticate itself with the proxy.
     */
    HttpStatusCode[HttpStatusCode["ProxyAuthenticationRequired"] = 407] = "ProxyAuthenticationRequired";
    /**
     * The server timed out waiting for the request.
     * According to HTTP specifications:
     * "The client did not produce a request within the time that the server was prepared to wait. The client MAY repeat the request without modifications at any later time."
     */
    HttpStatusCode[HttpStatusCode["RequestTimeout"] = 408] = "RequestTimeout";
    /**
     * Indicates that the request could not be processed because of conflict in the request,
     * such as an edit conflict between multiple simultaneous updates.
     */
    HttpStatusCode[HttpStatusCode["Conflict"] = 409] = "Conflict";
    /**
     * Indicates that the resource requested is no longer available and will not be available again.
     * This should be used when a resource has been intentionally removed and the resource should be purged.
     * Upon receiving a 410 status code, the client should not request the resource in the future.
     * Clients such as search engines should remove the resource from their indices.
     * Most use cases do not require clients and search engines to purge the resource, and a "404 Not Found" may be used instead.
     */
    HttpStatusCode[HttpStatusCode["Gone"] = 410] = "Gone";
    /**
     * The request did not specify the length of its content, which is required by the requested resource.
     */
    HttpStatusCode[HttpStatusCode["LengthRequired"] = 411] = "LengthRequired";
    /**
     * The server does not meet one of the preconditions that the requester put on the request.
     */
    HttpStatusCode[HttpStatusCode["PreconditionFailed"] = 412] = "PreconditionFailed";
    /**
     * The request is larger than the server is willing or able to process. Previously called "Request Entity Too Large".
     */
    HttpStatusCode[HttpStatusCode["PayloadTooLarge"] = 413] = "PayloadTooLarge";
    /**
     * The URI provided was too long for the server to process. Often the result of too much data being encoded as a query-string of a GET request,
     * in which case it should be converted to a POST request.
     * Called "Request-URI Too Long" previously.
     */
    HttpStatusCode[HttpStatusCode["UriTooLong"] = 414] = "UriTooLong";
    /**
     * The request entity has a media type which the server or resource does not support.
     * For example, the client uploads an image as image/svg+xml, but the server requires that images use a different format.
     */
    HttpStatusCode[HttpStatusCode["UnsupportedMediaType"] = 415] = "UnsupportedMediaType";
    /**
     * The client has asked for a portion of the file (byte serving), but the server cannot supply that portion.
     * For example, if the client asked for a part of the file that lies beyond the end of the file.
     * Called "Requested Range Not Satisfiable" previously.
     */
    HttpStatusCode[HttpStatusCode["RangeNotSatisfiable"] = 416] = "RangeNotSatisfiable";
    /**
     * The server cannot meet the requirements of the Expect request-header field.
     */
    HttpStatusCode[HttpStatusCode["ExpectationFailed"] = 417] = "ExpectationFailed";
    /**
     * This code was defined in 1998 as one of the traditional IETF April Fools' jokes, in RFC 2324, Hyper Text Coffee Pot Control Protocol,
     * and is not expected to be implemented by actual HTTP servers. The RFC specifies this code should be returned by
     * teapots requested to brew coffee. This HTTP status is used as an Easter egg in some websites, including Google.com.
     */
    HttpStatusCode[HttpStatusCode["IAmATeapot"] = 418] = "IAmATeapot";
    /**
     * The request was directed at a server that is not able to produce a response (for example because a connection reuse).
     */
    HttpStatusCode[HttpStatusCode["MisdirectedRequest"] = 421] = "MisdirectedRequest";
    /**
     * The request was well-formed but was unable to be followed due to semantic errors.
     */
    HttpStatusCode[HttpStatusCode["UnprocessableEntity"] = 422] = "UnprocessableEntity";
    /**
     * The resource that is being accessed is locked.
     */
    HttpStatusCode[HttpStatusCode["Locked"] = 423] = "Locked";
    /**
     * The request failed due to failure of a previous request (e.g., a PROPPATCH).
     */
    HttpStatusCode[HttpStatusCode["FailedDependency"] = 424] = "FailedDependency";
    /**
     * The client should switch to a different protocol such as TLS/1.0, given in the Upgrade header field.
     */
    HttpStatusCode[HttpStatusCode["UpgradeRequired"] = 426] = "UpgradeRequired";
    /**
     * The origin server requires the request to be conditional.
     * Intended to prevent "the 'lost update' problem, where a client
     * GETs a resource's state, modifies it, and PUTs it back to the server,
     * when meanwhile a third party has modified the state on the server, leading to a conflict."
     */
    HttpStatusCode[HttpStatusCode["PreconditionRequired"] = 428] = "PreconditionRequired";
    /**
     * The user has sent too many requests in a given amount of time. Intended for use with rate-limiting schemes.
     */
    HttpStatusCode[HttpStatusCode["TooManyRequests"] = 429] = "TooManyRequests";
    /**
     * The server is unwilling to process the request because either an individual header field,
     * or all the header fields collectively, are too large.
     */
    HttpStatusCode[HttpStatusCode["RequestHeaderFieldsTooLarge"] = 431] = "RequestHeaderFieldsTooLarge";
    /**
     * A server operator has received a legal demand to deny access to a resource or to a set of resources
     * that includes the requested resource. The code 451 was chosen as a reference to the novel Fahrenheit 451.
     */
    HttpStatusCode[HttpStatusCode["UnavailableForLegalReasons"] = 451] = "UnavailableForLegalReasons";
    // **********************************************************************************************************
    // 500s - Server messed up
    // **********************************************************************************************************
    /**
     * A generic error message, given when an unexpected condition was encountered and no more specific message is suitable.
     */
    HttpStatusCode[HttpStatusCode["InternalServerError"] = 500] = "InternalServerError";
    /**
     * The server either does not recognize the request method, or it lacks the ability to fulfill the request.
     * Usually this implies future availability (e.g., a new feature of a web-service API).
     */
    HttpStatusCode[HttpStatusCode["NotImplemented"] = 501] = "NotImplemented";
    /**
     * The server was acting as a gateway or proxy and received an invalid response from the upstream server.
     */
    HttpStatusCode[HttpStatusCode["BadGateway"] = 502] = "BadGateway";
    /**
     * The server is currently unavailable (because it is overloaded or down for maintenance).
     * Generally, this is a temporary state.
     */
    HttpStatusCode[HttpStatusCode["ServiceUnavailable"] = 503] = "ServiceUnavailable";
    /**
     * The server was acting as a gateway or proxy and did not receive a timely response from the upstream server.
     */
    HttpStatusCode[HttpStatusCode["GatewayTimeout"] = 504] = "GatewayTimeout";
    /**
     * The server does not support the HTTP protocol version used in the request
     */
    HttpStatusCode[HttpStatusCode["HttpVersionNotSupported"] = 505] = "HttpVersionNotSupported";
    /**
     * Transparent content negotiation for the request results in a circular reference.
     */
    HttpStatusCode[HttpStatusCode["VariantAlsoNegotiates"] = 506] = "VariantAlsoNegotiates";
    /**
     * The server is unable to store the representation needed to complete the request.
     */
    HttpStatusCode[HttpStatusCode["InsufficientStorage"] = 507] = "InsufficientStorage";
    /**
     * The server detected an infinite loop while processing the request.
     */
    HttpStatusCode[HttpStatusCode["LoopDetected"] = 508] = "LoopDetected";
    /**
     * Further extensions to the request are required for the server to fulfill it.
     */
    HttpStatusCode[HttpStatusCode["NotExtended"] = 510] = "NotExtended";
    /**
     * The client needs to authenticate to gain network access.
     * Intended for use by intercepting proxies used to control access to the network (e.g., "captive portals" used
     * to require agreement to Terms of Service before granting full Internet access via a Wi-Fi hotspot).
     */
    HttpStatusCode[HttpStatusCode["NetworkAuthenticationRequired"] = 511] = "NetworkAuthenticationRequired";
})(bw_HttpStatusCode || (bw_HttpStatusCode = {}));

;// ../../libs/common/src/enums/integration-type.enum.ts
var bw_IntegrationType;
(function (IntegrationType) {
    IntegrationType["Integration"] = "integration";
    IntegrationType["SDK"] = "sdk";
    IntegrationType["SSO"] = "sso";
    IntegrationType["SCIM"] = "scim";
    IntegrationType["BWDC"] = "bwdc";
    IntegrationType["EVENT"] = "event";
    IntegrationType["DEVICE"] = "device";
})(bw_IntegrationType || (bw_IntegrationType = {}));

;// ../../libs/common/src/enums/native-messaging-version.enum.ts
var bw_NativeMessagingVersion;
(function (NativeMessagingVersion) {
    NativeMessagingVersion[NativeMessagingVersion["One"] = 1] = "One";
    NativeMessagingVersion[NativeMessagingVersion["Latest"] = 1] = "Latest";
})(bw_NativeMessagingVersion || (bw_NativeMessagingVersion = {}));

;// ../../libs/common/src/enums/notification-type.enum.ts
var bw_NotificationType;
(function (NotificationType) {
    NotificationType[NotificationType["SyncCipherUpdate"] = 0] = "SyncCipherUpdate";
    NotificationType[NotificationType["SyncCipherCreate"] = 1] = "SyncCipherCreate";
    NotificationType[NotificationType["SyncLoginDelete"] = 2] = "SyncLoginDelete";
    NotificationType[NotificationType["SyncFolderDelete"] = 3] = "SyncFolderDelete";
    NotificationType[NotificationType["SyncCiphers"] = 4] = "SyncCiphers";
    NotificationType[NotificationType["SyncVault"] = 5] = "SyncVault";
    NotificationType[NotificationType["SyncOrgKeys"] = 6] = "SyncOrgKeys";
    NotificationType[NotificationType["SyncFolderCreate"] = 7] = "SyncFolderCreate";
    NotificationType[NotificationType["SyncFolderUpdate"] = 8] = "SyncFolderUpdate";
    NotificationType[NotificationType["SyncCipherDelete"] = 9] = "SyncCipherDelete";
    NotificationType[NotificationType["SyncSettings"] = 10] = "SyncSettings";
    NotificationType[NotificationType["LogOut"] = 11] = "LogOut";
    NotificationType[NotificationType["SyncSendCreate"] = 12] = "SyncSendCreate";
    NotificationType[NotificationType["SyncSendUpdate"] = 13] = "SyncSendUpdate";
    NotificationType[NotificationType["SyncSendDelete"] = 14] = "SyncSendDelete";
    NotificationType[NotificationType["AuthRequest"] = 15] = "AuthRequest";
    NotificationType[NotificationType["AuthRequestResponse"] = 16] = "AuthRequestResponse";
    NotificationType[NotificationType["SyncOrganizations"] = 17] = "SyncOrganizations";
    NotificationType[NotificationType["SyncOrganizationStatusChanged"] = 18] = "SyncOrganizationStatusChanged";
    NotificationType[NotificationType["SyncOrganizationCollectionSettingChanged"] = 19] = "SyncOrganizationCollectionSettingChanged";
})(bw_NotificationType || (bw_NotificationType = {}));

;// ../../libs/common/src/enums/index.ts









;// ../../libs/common/src/models/request/keys.request.ts
class bw_KeysRequest {
    constructor(publicKey, encryptedPrivateKey) {
        this.publicKey = publicKey;
        this.encryptedPrivateKey = encryptedPrivateKey;
    }
}

;// ../../libs/common/src/platform/models/domain/account.ts


class bw_EncryptionPair {
    toJSON() {
        return {
            encrypted: this.encrypted,
            decrypted: this.decrypted instanceof ArrayBuffer
                ? bw_utils_Utils.fromBufferToByteString(this.decrypted)
                : this.decrypted,
        };
    }
    static fromJSON(obj, decryptedFromJson, encryptedFromJson) {
        if (obj == null) {
            return null;
        }
        const pair = new bw_EncryptionPair();
        if ((obj === null || obj === void 0 ? void 0 : obj.encrypted) != null) {
            pair.encrypted = encryptedFromJson
                ? encryptedFromJson(obj.encrypted)
                : obj.encrypted;
        }
        if ((obj === null || obj === void 0 ? void 0 : obj.decrypted) != null) {
            pair.decrypted = decryptedFromJson
                ? decryptedFromJson(obj.decrypted)
                : obj.decrypted;
        }
        return pair;
    }
}
class bw_AccountKeys {
    constructor() {
        /** @deprecated July 2023, left for migration purposes*/
        this.cryptoSymmetricKey = new bw_EncryptionPair();
    }
    toJSON() {
        // If you pass undefined into fromBufferToByteString, you will get an empty string back
        // which will cause all sorts of headaches down the line when you try to getPublicKey
        // and expect a Uint8Array and get an empty string instead.
        return bw_utils_Utils.merge(this, {
            publicKey: this.publicKey ? bw_utils_Utils.fromBufferToByteString(this.publicKey) : undefined,
        });
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return Object.assign(new bw_AccountKeys(), obj, {
            cryptoSymmetricKey: bw_EncryptionPair.fromJSON(obj === null || obj === void 0 ? void 0 : obj.cryptoSymmetricKey, bw_SymmetricCryptoKey.fromJSON),
            publicKey: bw_utils_Utils.fromByteStringToArray(obj === null || obj === void 0 ? void 0 : obj.publicKey),
        });
    }
    static initRecordEncryptionPairsFromJSON(obj) {
        return bw_EncryptionPair.fromJSON(obj, (decObj) => {
            if (obj == null) {
                return null;
            }
            const record = {};
            for (const id in decObj) {
                record[id] = bw_SymmetricCryptoKey.fromJSON(decObj[id]);
            }
            return record;
        });
    }
}
class bw_AccountProfile {
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return Object.assign(new bw_AccountProfile(), obj);
    }
}
class bw_Account {
    constructor(init) {
        this.keys = new bw_AccountKeys();
        this.profile = new bw_AccountProfile();
        Object.assign(this, {
            keys: Object.assign(Object.assign({}, new bw_AccountKeys()), init === null || init === void 0 ? void 0 : init.keys),
            profile: Object.assign(Object.assign({}, new bw_AccountProfile()), init === null || init === void 0 ? void 0 : init.profile),
        });
    }
    static fromJSON(json) {
        if (json == null) {
            return null;
        }
        return Object.assign(new bw_Account({}), json, {
            keys: bw_AccountKeys.fromJSON(json === null || json === void 0 ? void 0 : json.keys),
            profile: bw_AccountProfile.fromJSON(json === null || json === void 0 ? void 0 : json.profile),
        });
    }
}

;// ../../libs/auth/src/common/login-strategies/login.strategy.ts
var bw_login_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};















class bw_LoginStrategyData {
}
class bw_LoginStrategy {
    constructor(accountService, masterPasswordService, keyService, encryptService, apiService, tokenService, appIdService, platformUtilsService, messagingService, logService, stateService, twoFactorService, userDecryptionOptionsService, billingAccountProfileStateService, vaultTimeoutSettingsService, KdfConfigService, environmentService) {
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.apiService = apiService;
        this.tokenService = tokenService;
        this.appIdService = appIdService;
        this.platformUtilsService = platformUtilsService;
        this.messagingService = messagingService;
        this.logService = logService;
        this.stateService = stateService;
        this.twoFactorService = twoFactorService;
        this.userDecryptionOptionsService = userDecryptionOptionsService;
        this.billingAccountProfileStateService = billingAccountProfileStateService;
        this.vaultTimeoutSettingsService = vaultTimeoutSettingsService;
        this.KdfConfigService = KdfConfigService;
        this.environmentService = environmentService;
        this.sessionTimeoutSubject = new bw_external_rxjs_namespaceObject.BehaviorSubject(false);
        this.sessionTimeout$ = this.sessionTimeoutSubject.asObservable();
    }
    logInTwoFactor(twoFactor_1) {
        return bw_login_strategy_awaiter(this, arguments, void 0, function* (twoFactor, captchaResponse = null) {
            const data = this.cache.value;
            if (!data.tokenRequest) {
                throw new Error("Token request is undefined");
            }
            data.tokenRequest.setTwoFactor(twoFactor);
            this.cache.next(data);
            const [authResult] = yield this.startLogIn();
            return authResult;
        });
    }
    startLogIn() {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            yield this.twoFactorService.clearSelectedProvider();
            const tokenRequest = this.cache.value.tokenRequest;
            if (!tokenRequest) {
                throw new Error("Token request is undefined");
            }
            const response = yield this.apiService.postIdentityToken(tokenRequest);
            if (response instanceof bw_IdentityTwoFactorResponse) {
                return [yield this.processTwoFactorResponse(response), response];
            }
            else if (response instanceof bw_IdentityCaptchaResponse) {
                return [yield this.processCaptchaResponse(response), response];
            }
            else if (response instanceof bw_IdentityTokenResponse) {
                return [yield this.processTokenResponse(response), response];
            }
            else if (response instanceof bw_IdentityDeviceVerificationResponse) {
                return [yield this.processDeviceVerificationResponse(response), response];
            }
            throw new Error("Invalid response object.");
        });
    }
    buildDeviceRequest() {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            const appId = yield this.appIdService.getAppId();
            return new bw_DeviceRequest(appId, this.platformUtilsService);
        });
    }
    /**
     * Builds the TokenTwoFactorRequest to be used within other login strategies token requests
     * to the server.
     * If the user provided a 2FA token in an already created TokenTwoFactorRequest, it will be used.
     * If not, and the user has previously remembered a 2FA token, it will be used.
     * If neither of these are true, an empty TokenTwoFactorRequest will be returned.
     * @param userProvidedTwoFactor - optional - The 2FA token request provided by the caller
     * @param email - optional - ensure that email is provided for any login strategies that support remember 2FA functionality
     * @returns a promise which resolves to a TokenTwoFactorRequest to be sent to the server
     */
    buildTwoFactor(userProvidedTwoFactor, email) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            if (userProvidedTwoFactor != null) {
                return userProvidedTwoFactor;
            }
            if (email) {
                const storedTwoFactorToken = yield this.tokenService.getTwoFactorToken(email);
                if (storedTwoFactorToken != null) {
                    return new bw_TokenTwoFactorRequest(bw_TwoFactorProviderType.Remember, storedTwoFactorToken, false);
                }
            }
            return new bw_TokenTwoFactorRequest();
        });
    }
    /**
     * Initializes the account with information from the IdTokenResponse after successful login.
     * It also sets the access token and refresh token in the token service.
     *
     * @param {IdentityTokenResponse} tokenResponse - The response from the server containing the identity token.
     * @returns {Promise<UserId>} - A promise that resolves the the UserId when the account information has been successfully saved.
     */
    saveAccountInformation(tokenResponse) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a, _b, _c;
            const accountInformation = yield this.tokenService.decodeAccessToken(tokenResponse.accessToken);
            const userId = accountInformation.sub;
            yield this.accountService.addAccount(userId, {
                name: accountInformation.name,
                email: (_a = accountInformation.email) !== null && _a !== void 0 ? _a : "",
                emailVerified: (_b = accountInformation.email_verified) !== null && _b !== void 0 ? _b : false,
            });
            // User env must be seeded from currently set env before switching to the account
            // to avoid any incorrect emissions of the global default env.
            yield this.environmentService.seedUserEnvironment(userId);
            yield this.accountService.switchAccount(userId);
            yield this.stateService.addAccount(new bw_Account({
                profile: Object.assign(Object.assign({}, new bw_AccountProfile()), {
                    userId,
                    name: accountInformation.name,
                    email: accountInformation.email,
                }),
            }));
            yield this.verifyAccountAdded(userId);
            // We must set user decryption options before retrieving vault timeout settings
            // as the user decryption options help determine the available timeout actions.
            yield this.userDecryptionOptionsService.setUserDecryptionOptions(bw_UserDecryptionOptions.fromResponse(tokenResponse));
            const vaultTimeoutAction = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutActionByUserId$(userId));
            const vaultTimeout = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutByUserId$(userId));
            // User id will be derived from the access token.
            yield this.tokenService.setTokens(tokenResponse.accessToken, vaultTimeoutAction, vaultTimeout, tokenResponse.refreshToken);
            yield this.KdfConfigService.setKdfConfig(userId, tokenResponse.kdf === bw_KdfType.PBKDF2_SHA256
                ? new bw_PBKDF2KdfConfig(tokenResponse.kdfIterations)
                : new bw_Argon2KdfConfig(tokenResponse.kdfIterations, tokenResponse.kdfMemory, tokenResponse.kdfParallelism));
            yield this.billingAccountProfileStateService.setHasPremium((_c = accountInformation.premium) !== null && _c !== void 0 ? _c : false, false, userId);
            return userId;
        });
    }
    processTokenResponse(response) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            const result = new bw_AuthResult();
            // Old encryption keys must be migrated, but is currently only available on web.
            // Other clients shouldn't continue the login process.
            if (this.encryptionKeyMigrationRequired(response)) {
                result.requiresEncryptionKeyMigration = true;
                if (this.platformUtilsService.getClientType() !== bw_ClientType.Web) {
                    return result;
                }
            }
            // Must come before setting keys, user key needs email to update additional keys.
            const userId = yield this.saveAccountInformation(response);
            result.userId = userId;
            result.resetMasterPassword = response.resetMasterPassword;
            // Convert boolean to enum and set the state for the master password service to
            // so we know when we reach the auth guard that we need to guide them properly to admin
            // password reset.
            if (response.forcePasswordReset) {
                result.forcePasswordReset = bw_ForceSetPasswordReason.AdminForcePasswordReset;
                yield this.masterPasswordService.setForceSetPasswordReason(bw_ForceSetPasswordReason.AdminForcePasswordReset, userId);
            }
            if (response.twoFactorToken != null) {
                // note: we can read email from access token b/c it was saved in saveAccountInformation
                const userEmail = yield this.tokenService.getEmail();
                yield this.tokenService.setTwoFactorToken(userEmail, response.twoFactorToken);
            }
            yield this.setMasterKey(response, userId);
            yield this.setUserKey(response, userId);
            yield this.setPrivateKey(response, userId);
            this.messagingService.send("loggedIn");
            return result;
        });
    }
    // Old accounts used master key for encryption. We are forcing migrations but only need to
    // check on password logins
    encryptionKeyMigrationRequired(response) {
        return false;
    }
    createKeyPairForOldAccount(userId) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            try {
                const userKey = yield this.keyService.getUserKeyWithLegacySupport(userId);
                const [publicKey, privateKey] = yield this.keyService.makeKeyPair(userKey);
                if (!privateKey.encryptedString) {
                    throw new Error("Failed to create encrypted private key");
                }
                yield this.apiService.postAccountKeys(new bw_KeysRequest(publicKey, privateKey.encryptedString));
                return privateKey.encryptedString;
            }
            catch (e) {
                this.logService.error(e);
            }
        });
    }
    /**
     * Handles the response from the server when a 2FA is required.
     * It clears any existing 2FA token, as it's no longer valid, and sets up the necessary data for the 2FA process.
     *
     * @param {IdentityTwoFactorResponse} response - The response from the server indicating that 2FA is required.
     * @returns {Promise<AuthResult>} - A promise that resolves to an AuthResult object
     */
    processTwoFactorResponse(response) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            // If we get a 2FA required response, then we should clear the 2FA token
            // just in case as it is no longer valid.
            yield this.clearTwoFactorToken();
            const result = new bw_AuthResult();
            result.twoFactorProviders = response.twoFactorProviders2;
            yield this.twoFactorService.setProviders(response);
            this.cache.next(Object.assign(Object.assign({}, this.cache.value), { captchaBypassToken: (_a = response.captchaToken) !== null && _a !== void 0 ? _a : null }));
            result.ssoEmail2FaSessionToken = response.ssoEmail2faSessionToken;
            result.email = (_b = response.email) !== null && _b !== void 0 ? _b : "";
            return result;
        });
    }
    /**
     * Clears the 2FA token from the token service using the user's email if it exists
     */
    clearTwoFactorToken() {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            const email = this.cache.value.userEnteredEmail;
            if (email) {
                yield this.tokenService.clearTwoFactorToken(email);
            }
        });
    }
    processCaptchaResponse(response) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            const result = new bw_AuthResult();
            result.captchaSiteKey = response.siteKey;
            return result;
        });
    }
    /**
     * Verifies that the active account is set after initialization.
     * Note: In browser there is a slight delay between when active account emits in background,
     * and when it emits in foreground. We're giving the foreground 1 second to catch up.
     * If nothing is emitted, we throw an error.
     */
    verifyAccountAdded(expectedUserId) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.filter)((account) => (account === null || account === void 0 ? void 0 : account.id) === expectedUserId), (0,bw_external_rxjs_namespaceObject.timeout)({
                first: 1000,
                with: () => {
                    throw new Error("Expected user never made active user after initialization.");
                },
            })));
        });
    }
    /**
     * Handles the response from the server when a device verification is required.
     * It sets the requiresDeviceVerification flag to true and caches the captcha token if it came back.
     *
     * @param {IdentityDeviceVerificationResponse} response - The response from the server indicating that device verification is required.
     * @returns {Promise<AuthResult>} - A promise that resolves to an AuthResult object
     */
    processDeviceVerificationResponse(response) {
        return bw_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            const result = new bw_AuthResult();
            result.requiresDeviceVerification = true;
            // Extend cached data with captcha bypass token if it came back.
            this.cache.next(Object.assign(Object.assign({}, this.cache.value), { captchaBypassToken: (_a = response.captchaToken) !== null && _a !== void 0 ? _a : null }));
            return result;
        });
    }
}

;// ../../libs/auth/src/common/login-strategies/auth-request-login.strategy.ts
var bw_auth_request_login_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_AuthRequestLoginStrategyData {
    static fromJSON(obj) {
        const data = Object.assign(new bw_AuthRequestLoginStrategyData(), obj, {
            tokenRequest: bw_PasswordTokenRequest.fromJSON(obj.tokenRequest),
            authRequestCredentials: bw_AuthRequestLoginCredentials.fromJSON(obj.authRequestCredentials),
        });
        return data;
    }
}
class bw_AuthRequestLoginStrategy extends bw_LoginStrategy {
    constructor(data, deviceTrustService, ...sharedDeps) {
        super(...sharedDeps);
        this.deviceTrustService = deviceTrustService;
        this.cache = new bw_external_rxjs_namespaceObject.BehaviorSubject(data);
        this.email$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((data) => data.tokenRequest.email));
        this.accessCode$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((data) => data.authRequestCredentials.accessCode));
        this.authRequestId$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((data) => data.authRequestCredentials.authRequestId));
    }
    logIn(credentials) {
        return bw_auth_request_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = new bw_AuthRequestLoginStrategyData();
            data.tokenRequest = new bw_PasswordTokenRequest(credentials.email, credentials.accessCode, null, yield this.buildTwoFactor(credentials.twoFactor, credentials.email), yield this.buildDeviceRequest());
            data.tokenRequest.setAuthRequestAccessCode(credentials.authRequestId);
            data.authRequestCredentials = credentials;
            this.cache.next(data);
            const [authResult] = yield this.startLogIn();
            return authResult;
        });
    }
    logInTwoFactor(twoFactor, captchaResponse) {
        const _super = Object.create(null, {
            logInTwoFactor: { get: () => super.logInTwoFactor }
        });
        return bw_auth_request_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = this.cache.value;
            data.tokenRequest.captchaResponse = captchaResponse !== null && captchaResponse !== void 0 ? captchaResponse : data.captchaBypassToken;
            this.cache.next(data);
            return _super.logInTwoFactor.call(this, twoFactor);
        });
    }
    setMasterKey(response, userId) {
        return bw_auth_request_login_strategy_awaiter(this, void 0, void 0, function* () {
            const authRequestCredentials = this.cache.value.authRequestCredentials;
            if (authRequestCredentials.decryptedMasterKey &&
                authRequestCredentials.decryptedMasterKeyHash) {
                yield this.masterPasswordService.setMasterKey(authRequestCredentials.decryptedMasterKey, userId);
                yield this.masterPasswordService.setMasterKeyHash(authRequestCredentials.decryptedMasterKeyHash, userId);
            }
        });
    }
    setUserKey(response, userId) {
        return bw_auth_request_login_strategy_awaiter(this, void 0, void 0, function* () {
            const authRequestCredentials = this.cache.value.authRequestCredentials;
            // User now may or may not have a master password
            // but set the master key encrypted user key if it exists regardless
            yield this.keyService.setMasterKeyEncryptedUserKey(response.key, userId);
            if (authRequestCredentials.decryptedUserKey) {
                yield this.keyService.setUserKey(authRequestCredentials.decryptedUserKey, userId);
            }
            else {
                yield this.trySetUserKeyWithMasterKey(userId);
                // Establish trust if required after setting user key
                yield this.deviceTrustService.trustDeviceIfRequired(userId);
            }
        });
    }
    trySetUserKeyWithMasterKey(userId) {
        return bw_auth_request_login_strategy_awaiter(this, void 0, void 0, function* () {
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            if (masterKey) {
                const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId);
                yield this.keyService.setUserKey(userKey, userId);
            }
        });
    }
    setPrivateKey(response, userId) {
        return bw_auth_request_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            yield this.keyService.setPrivateKey((_a = response.privateKey) !== null && _a !== void 0 ? _a : (yield this.createKeyPairForOldAccount(userId)), userId);
        });
    }
    exportCache() {
        return {
            authRequest: this.cache.value,
        };
    }
}

;// ../../libs/common/src/platform/models/domain/domain-base.ts
var bw_domain_base_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// https://contributing.bitwarden.com/architecture/clients/data-model#domain
class bw_domain_base_Domain {
    buildDomainModel(domain, dataObj, map, notEncList = []) {
        for (const prop in map) {
            // eslint-disable-next-line
            if (!map.hasOwnProperty(prop)) {
                continue;
            }
            const objProp = dataObj[map[prop] || prop];
            if (notEncList.indexOf(prop) > -1) {
                domain[prop] = objProp ? objProp : null;
            }
            else {
                domain[prop] = objProp ? new bw_enc_string_EncString(objProp) : null;
            }
        }
    }
    buildDataModel(domain, dataObj, map, notEncStringList = []) {
        for (const prop in map) {
            // eslint-disable-next-line
            if (!map.hasOwnProperty(prop)) {
                continue;
            }
            const objProp = domain[map[prop] || prop];
            if (notEncStringList.indexOf(prop) > -1) {
                dataObj[prop] = objProp != null ? objProp : null;
            }
            else {
                dataObj[prop] = objProp != null ? objProp.encryptedString : null;
            }
        }
    }
    decryptObj(domain_1, viewModel_1, props_1, orgId_1) {
        return bw_domain_base_awaiter(this, arguments, void 0, function* (domain, viewModel, props, orgId, key = null, objectContext = "No Domain Context") {
            var _a, _b;
            for (const prop of props) {
                viewModel[prop] =
                    (_b = (yield ((_a = domain[prop]) === null || _a === void 0 ? void 0 : _a.decrypt(orgId, key, `Property: ${prop}; ObjectContext: ${objectContext}`)))) !== null && _b !== void 0 ? _b : null;
            }
            return viewModel;
        });
    }
    /**
     * Decrypts the requested properties of the domain object with the provided key and encrypt service.
     *
     * If a property is null, the result will be null.
     * @see {@link EncString.decryptWithKey} for more details on decryption behavior.
     *
     * @param encryptedProperties The properties to decrypt. Type restricted to EncString properties of the domain object.
     * @param key The key to use for decryption.
     * @param encryptService The encryption service to use for decryption.
     * @param _ The constructor of the domain object. Used for type inference if the domain object is not automatically inferred.
     * @returns An object with the requested properties decrypted and the rest of the domain object untouched.
     */
    decryptObjWithKey(encryptedProperties_1, key_1, encryptService_1) {
        return bw_domain_base_awaiter(this, arguments, void 0, function* (encryptedProperties, key, encryptService, _ = this.constructor, objectContext = "No Domain Context") {
            const decryptedObjects = [];
            for (const prop of encryptedProperties) {
                const value = this[prop];
                const decrypted = yield this.decryptProperty(prop, value, key, encryptService, `Property: ${prop.toString()}; ObjectContext: ${objectContext}`);
                decryptedObjects.push(decrypted);
            }
            const decryptedObject = decryptedObjects.reduce((acc, obj) => {
                return Object.assign(Object.assign({}, acc), obj);
            }, Object.assign({}, this));
            return decryptedObject;
        });
    }
    decryptProperty(propertyKey, value, key, encryptService, decryptTrace) {
        return bw_domain_base_awaiter(this, void 0, void 0, function* () {
            let decrypted = null;
            if (value) {
                decrypted = yield value.decryptWithKey(key, encryptService, decryptTrace);
            }
            return {
                [propertyKey]: decrypted,
            };
        });
    }
}

;// ../../libs/common/src/admin-console/models/domain/master-password-policy-options.ts

class bw_MasterPasswordPolicyOptions extends bw_domain_base_Domain {
    constructor() {
        super(...arguments);
        this.minComplexity = 0;
        this.minLength = 0;
        this.requireUpper = false;
        this.requireLower = false;
        this.requireNumbers = false;
        this.requireSpecial = false;
        /**
         * Flag to indicate if the policy should be enforced on login.
         * If true, and the user's password does not meet the policy requirements,
         * the user will be forced to update their password.
         */
        this.enforceOnLogin = false;
    }
    static fromResponse(policy) {
        if (policy == null) {
            return null;
        }
        const options = new bw_MasterPasswordPolicyOptions();
        options.minComplexity = policy.minComplexity;
        options.minLength = policy.minLength;
        options.requireUpper = policy.requireUpper;
        options.requireLower = policy.requireLower;
        options.requireNumbers = policy.requireNumbers;
        options.requireSpecial = policy.requireSpecial;
        options.enforceOnLogin = policy.enforceOnLogin;
        return options;
    }
}

;// ../../libs/auth/src/common/login-strategies/password-login.strategy.ts
var bw_password_login_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










class bw_PasswordLoginStrategyData {
    constructor() {
        /**
         * Tracks if the user needs to update their password due to
         * a password that does not meet an organization's master password policy.
         */
        this.forcePasswordResetReason = bw_ForceSetPasswordReason.None;
    }
    static fromJSON(obj) {
        const data = Object.assign(new bw_PasswordLoginStrategyData(), obj, {
            tokenRequest: bw_PasswordTokenRequest.fromJSON(obj.tokenRequest),
            masterKey: bw_SymmetricCryptoKey.fromJSON(obj.masterKey),
        });
        return data;
    }
}
class bw_PasswordLoginStrategy extends bw_LoginStrategy {
    constructor(data, passwordStrengthService, policyService, loginStrategyService, ...sharedDeps) {
        super(...sharedDeps);
        this.passwordStrengthService = passwordStrengthService;
        this.policyService = policyService;
        this.loginStrategyService = loginStrategyService;
        this.cache = new bw_external_rxjs_namespaceObject.BehaviorSubject(data);
        this.email$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => state.tokenRequest.email));
        this.serverMasterKeyHash$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => state.tokenRequest.masterPasswordHash));
        this.localMasterKeyHash$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => state.localMasterKeyHash));
    }
    logIn(credentials) {
        return bw_password_login_strategy_awaiter(this, void 0, void 0, function* () {
            const { email, masterPassword, captchaToken, twoFactor } = credentials;
            const data = new bw_PasswordLoginStrategyData();
            data.masterKey = yield this.loginStrategyService.makePreloginKey(masterPassword, email);
            data.userEnteredEmail = email;
            // Hash the password early (before authentication) so we don't persist it in memory in plaintext
            data.localMasterKeyHash = yield this.keyService.hashMasterKey(masterPassword, data.masterKey, bw_HashPurpose.LocalAuthorization);
            const serverMasterKeyHash = yield this.keyService.hashMasterKey(masterPassword, data.masterKey);
            data.tokenRequest = new bw_PasswordTokenRequest(email, serverMasterKeyHash, captchaToken, yield this.buildTwoFactor(twoFactor, email), yield this.buildDeviceRequest());
            this.cache.next(data);
            const [authResult, identityResponse] = yield this.startLogIn();
            if (identityResponse instanceof bw_IdentityCaptchaResponse) {
                return authResult;
            }
            const masterPasswordPolicyOptions = this.getMasterPasswordPolicyOptionsFromResponse(identityResponse);
            // The identity result can contain master password policies for the user's organizations
            if (masterPasswordPolicyOptions === null || masterPasswordPolicyOptions === void 0 ? void 0 : masterPasswordPolicyOptions.enforceOnLogin) {
                // If there is a policy active, evaluate the supplied password before its no longer in memory
                const meetsRequirements = this.evaluateMasterPassword(credentials, masterPasswordPolicyOptions);
                if (meetsRequirements) {
                    return authResult;
                }
                if (identityResponse instanceof bw_IdentityTwoFactorResponse) {
                    // Save the flag to this strategy for use in 2fa login as the master password is about to pass out of scope
                    this.cache.next(Object.assign(Object.assign({}, this.cache.value), { forcePasswordResetReason: bw_ForceSetPasswordReason.WeakMasterPassword }));
                }
                else {
                    // Authentication was successful, save the force update password options with the state service
                    yield this.masterPasswordService.setForceSetPasswordReason(bw_ForceSetPasswordReason.WeakMasterPassword, authResult.userId);
                    authResult.forcePasswordReset = bw_ForceSetPasswordReason.WeakMasterPassword;
                }
            }
            return authResult;
        });
    }
    logInTwoFactor(twoFactor, captchaResponse) {
        const _super = Object.create(null, {
            logInTwoFactor: { get: () => super.logInTwoFactor }
        });
        return bw_password_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = this.cache.value;
            data.tokenRequest.captchaResponse = captchaResponse !== null && captchaResponse !== void 0 ? captchaResponse : data.captchaBypassToken;
            this.cache.next(data);
            const result = yield _super.logInTwoFactor.call(this, twoFactor);
            // 2FA was successful, save the force update password options with the state service if defined
            const forcePasswordResetReason = this.cache.value.forcePasswordResetReason;
            if (!result.requiresTwoFactor &&
                !result.requiresCaptcha &&
                forcePasswordResetReason != bw_ForceSetPasswordReason.None) {
                yield this.masterPasswordService.setForceSetPasswordReason(forcePasswordResetReason, result.userId);
                result.forcePasswordReset = forcePasswordResetReason;
            }
            return result;
        });
    }
    setMasterKey(response, userId) {
        return bw_password_login_strategy_awaiter(this, void 0, void 0, function* () {
            const { masterKey, localMasterKeyHash } = this.cache.value;
            yield this.masterPasswordService.setMasterKey(masterKey, userId);
            yield this.masterPasswordService.setMasterKeyHash(localMasterKeyHash, userId);
        });
    }
    setUserKey(response, userId) {
        return bw_password_login_strategy_awaiter(this, void 0, void 0, function* () {
            // If migration is required, we won't have a user key to set yet.
            if (this.encryptionKeyMigrationRequired(response)) {
                return;
            }
            yield this.keyService.setMasterKeyEncryptedUserKey(response.key, userId);
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            if (masterKey) {
                const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId);
                yield this.keyService.setUserKey(userKey, userId);
            }
        });
    }
    setPrivateKey(response, userId) {
        return bw_password_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            yield this.keyService.setPrivateKey((_a = response.privateKey) !== null && _a !== void 0 ? _a : (yield this.createKeyPairForOldAccount(userId)), userId);
        });
    }
    encryptionKeyMigrationRequired(response) {
        return !response.key;
    }
    getMasterPasswordPolicyOptionsFromResponse(response) {
        if (response == null || response instanceof bw_IdentityDeviceVerificationResponse) {
            return null;
        }
        return bw_MasterPasswordPolicyOptions.fromResponse(response.masterPasswordPolicy);
    }
    evaluateMasterPassword({ masterPassword, email }, options) {
        var _a;
        const passwordStrength = (_a = this.passwordStrengthService.getPasswordStrength(masterPassword, email)) === null || _a === void 0 ? void 0 : _a.score;
        return this.policyService.evaluateMasterPassword(passwordStrength, masterPassword, options);
    }
    exportCache() {
        return {
            password: this.cache.value,
        };
    }
    logInNewDeviceVerification(deviceVerificationOtp) {
        return bw_password_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = this.cache.value;
            data.tokenRequest.newDeviceOtp = deviceVerificationOtp;
            this.cache.next(data);
            const [authResult] = yield this.startLogIn();
            return authResult;
        });
    }
}

;// ../../libs/common/src/auth/models/request/identity-token/sso-token.request.ts



class bw_SsoTokenRequest extends bw_TokenRequest {
    constructor(code, codeVerifier, redirectUri, twoFactor, device) {
        super(twoFactor, device);
        this.code = code;
        this.codeVerifier = codeVerifier;
        this.redirectUri = redirectUri;
        this.twoFactor = twoFactor;
    }
    toIdentityToken(clientId) {
        const obj = super.toIdentityToken(clientId);
        obj.grant_type = "authorization_code";
        obj.code = this.code;
        obj.code_verifier = this.codeVerifier;
        obj.redirect_uri = this.redirectUri;
        return obj;
    }
    static fromJSON(json) {
        return Object.assign(Object.create(bw_SsoTokenRequest.prototype), json, {
            device: json.device ? bw_DeviceRequest.fromJSON(json.device) : undefined,
            twoFactor: json.twoFactor
                ? Object.assign(new bw_TokenTwoFactorRequest(), json.twoFactor)
                : undefined,
        });
    }
}

;// ../../libs/auth/src/common/login-strategies/sso-login.strategy.ts
var bw_sso_login_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_SsoLoginStrategyData {
    static fromJSON(obj) {
        return Object.assign(new bw_SsoLoginStrategyData(), obj, {
            tokenRequest: bw_SsoTokenRequest.fromJSON(obj.tokenRequest),
        });
    }
}
class bw_SsoLoginStrategy extends bw_LoginStrategy {
    constructor(data, keyConnectorService, deviceTrustService, authRequestService, i18nService, ...sharedDeps) {
        super(...sharedDeps);
        this.keyConnectorService = keyConnectorService;
        this.deviceTrustService = deviceTrustService;
        this.authRequestService = authRequestService;
        this.i18nService = i18nService;
        this.cache = new bw_external_rxjs_namespaceObject.BehaviorSubject(data);
        this.email$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => state.email));
        this.orgId$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => state.orgId));
        this.ssoEmail2FaSessionToken$ = this.cache.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => state.ssoEmail2FaSessionToken));
    }
    logIn(credentials) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = new bw_SsoLoginStrategyData();
            data.orgId = credentials.orgId;
            data.userEnteredEmail = credentials.email;
            const deviceRequest = yield this.buildDeviceRequest();
            this.logService.info("Logging in with appId %s.", deviceRequest.identifier);
            data.tokenRequest = new bw_SsoTokenRequest(credentials.code, credentials.codeVerifier, credentials.redirectUrl, yield this.buildTwoFactor(credentials.twoFactor, credentials.email), deviceRequest);
            this.cache.next(data);
            const [ssoAuthResult] = yield this.startLogIn();
            const email = ssoAuthResult.email;
            const ssoEmail2FaSessionToken = ssoAuthResult.ssoEmail2FaSessionToken;
            this.cache.next(Object.assign(Object.assign({}, this.cache.value), { email,
                ssoEmail2FaSessionToken }));
            return ssoAuthResult;
        });
    }
    setMasterKey(tokenResponse, userId) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            // The only way we can be setting a master key at this point is if we are using Key Connector.
            // First, check to make sure that we should do so based on the token response.
            if (this.shouldSetMasterKeyFromKeyConnector(tokenResponse)) {
                // If we're here, we know that the user should use Key Connector (they have a KeyConnectorUrl) and does not have a master password.
                // We can now check the key on the token response to see whether they are a brand new user or an existing user.
                // The presence of a masterKeyEncryptedUserKey indicates that the user has already been provisioned in Key Connector.
                const newSsoUser = tokenResponse.key == null;
                if (newSsoUser) {
                    yield this.keyConnectorService.convertNewSsoUserToKeyConnector(tokenResponse, this.cache.value.orgId, userId);
                }
                else {
                    const keyConnectorUrl = this.getKeyConnectorUrl(tokenResponse);
                    yield this.keyConnectorService.setMasterKeyFromUrl(keyConnectorUrl, userId);
                }
            }
        });
    }
    /**
     * Determines if it is possible set the `masterKey` from Key Connector.
     * @param tokenResponse
     * @returns `true` if the master key can be set from Key Connector, `false` otherwise
     */
    shouldSetMasterKeyFromKeyConnector(tokenResponse) {
        var _a;
        const userDecryptionOptions = tokenResponse === null || tokenResponse === void 0 ? void 0 : tokenResponse.userDecryptionOptions;
        if (userDecryptionOptions != null) {
            const userHasMasterPassword = userDecryptionOptions.hasMasterPassword;
            const userHasKeyConnectorUrl = ((_a = userDecryptionOptions.keyConnectorOption) === null || _a === void 0 ? void 0 : _a.keyConnectorUrl) != null;
            // In order for us to set the master key from Key Connector, we need to have a Key Connector URL
            // and the user must not have a master password.
            return userHasKeyConnectorUrl && !userHasMasterPassword;
        }
        else {
            // In pre-TDE versions of the server, the userDecryptionOptions will not be present.
            // In this case, we can determine if the user has a master password and has a Key Connector URL by
            // just checking the keyConnectorUrl property. This is because the server short-circuits on the response
            // and will not pass back the URL in the response if the user has a master password.
            // TODO: remove compatibility check after 2023.10 release (https://bitwarden.atlassian.net/browse/PM-3537)
            return tokenResponse.keyConnectorUrl != null;
        }
    }
    getKeyConnectorUrl(tokenResponse) {
        var _a, _b;
        // TODO: remove tokenResponse.keyConnectorUrl reference after 2023.10 release (https://bitwarden.atlassian.net/browse/PM-3537)
        const userDecryptionOptions = tokenResponse === null || tokenResponse === void 0 ? void 0 : tokenResponse.userDecryptionOptions;
        return ((_a = tokenResponse.keyConnectorUrl) !== null && _a !== void 0 ? _a : (_b = userDecryptionOptions === null || userDecryptionOptions === void 0 ? void 0 : userDecryptionOptions.keyConnectorOption) === null || _b === void 0 ? void 0 : _b.keyConnectorUrl);
    }
    // TODO: future passkey login strategy will need to support setting user key (decrypting via TDE or admin approval request)
    // so might be worth moving this logic to a common place (base login strategy or a separate service?)
    setUserKey(tokenResponse, userId) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            const masterKeyEncryptedUserKey = tokenResponse.key;
            // Note: masterKeyEncryptedUserKey is undefined for SSO JIT provisioned users
            // on account creation and subsequent logins (confirmed or unconfirmed)
            // but that is fine for TDE so we cannot return if it is undefined
            if (masterKeyEncryptedUserKey) {
                // set the master key encrypted user key if it exists
                yield this.keyService.setMasterKeyEncryptedUserKey(masterKeyEncryptedUserKey, userId);
            }
            const userDecryptionOptions = tokenResponse === null || tokenResponse === void 0 ? void 0 : tokenResponse.userDecryptionOptions;
            // Note: TDE and key connector are mutually exclusive
            if (userDecryptionOptions === null || userDecryptionOptions === void 0 ? void 0 : userDecryptionOptions.trustedDeviceOption) {
                this.logService.info("Attempting to set user key with approved admin auth request.");
                // Try to use the user key from an approved admin request if it exists.
                // Using it will clear it from state and future requests will use the device key.
                yield this.trySetUserKeyWithApprovedAdminRequestIfExists(userId);
                const hasUserKey = yield this.keyService.hasUserKey(userId);
                // Only try to set user key with device key if admin approval request was not successful.
                if (!hasUserKey) {
                    this.logService.info("Attempting to set user key with device key.");
                    yield this.trySetUserKeyWithDeviceKey(tokenResponse, userId);
                }
            }
            else if (masterKeyEncryptedUserKey != null &&
                this.getKeyConnectorUrl(tokenResponse) != null) {
                // Key connector enabled for user
                yield this.trySetUserKeyWithMasterKey(userId);
            }
            // Note: In the traditional SSO flow with MP without key connector, the lock component
            // is responsible for deriving master key from MP entry and then decrypting the user key
        });
    }
    trySetUserKeyWithApprovedAdminRequestIfExists(userId) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            // At this point a user could have an admin auth request that has been approved
            const adminAuthReqStorable = yield this.authRequestService.getAdminAuthRequest(userId);
            if (!adminAuthReqStorable) {
                return;
            }
            // Call server to see if admin auth request has been approved
            let adminAuthReqResponse;
            try {
                adminAuthReqResponse = yield this.apiService.getAuthRequest(adminAuthReqStorable.id);
            }
            catch (error) {
                if (error instanceof bw_ErrorResponse && error.statusCode === bw_HttpStatusCode.NotFound) {
                    // if we get a 404, it means the auth request has been deleted so clear it from storage
                    yield this.authRequestService.clearAdminAuthRequest(userId);
                }
                // Always return on an error here as we don't want to block the user from logging in
                return;
            }
            if (adminAuthReqResponse === null || adminAuthReqResponse === void 0 ? void 0 : adminAuthReqResponse.requestApproved) {
                // if masterPasswordHash has a value, we will always receive authReqResponse.key
                // as authRequestPublicKey(masterKey) + authRequestPublicKey(masterPasswordHash)
                if (adminAuthReqResponse.masterPasswordHash) {
                    yield this.authRequestService.setKeysAfterDecryptingSharedMasterKeyAndHash(adminAuthReqResponse, adminAuthReqStorable.privateKey, userId);
                }
                else {
                    // if masterPasswordHash is null, we will always receive authReqResponse.key
                    // as authRequestPublicKey(userKey)
                    yield this.authRequestService.setUserKeyAfterDecryptingSharedUserKey(adminAuthReqResponse, adminAuthReqStorable.privateKey, userId);
                }
                if (yield this.keyService.hasUserKey()) {
                    // Now that we have a decrypted user key in memory, we can check if we
                    // need to establish trust on the current device
                    yield this.deviceTrustService.trustDeviceIfRequired(userId);
                    // if we successfully decrypted the user key, we can delete the admin auth request out of state
                    // TODO: eventually we post and clean up DB as well once consumed on client
                    yield this.authRequestService.clearAdminAuthRequest(userId);
                    // This notification will be picked up by the SsoComponent to handle displaying a toast to the user
                    this.authRequestService.emitAdminLoginApproved();
                }
            }
        });
    }
    trySetUserKeyWithDeviceKey(tokenResponse, userId) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            const trustedDeviceOption = (_a = tokenResponse.userDecryptionOptions) === null || _a === void 0 ? void 0 : _a.trustedDeviceOption;
            if (!trustedDeviceOption) {
                this.logService.error("Unable to set user key due to missing trustedDeviceOption.");
                return;
            }
            const deviceKey = yield this.deviceTrustService.getDeviceKey(userId);
            const encDevicePrivateKey = trustedDeviceOption === null || trustedDeviceOption === void 0 ? void 0 : trustedDeviceOption.encryptedPrivateKey;
            const encUserKey = trustedDeviceOption === null || trustedDeviceOption === void 0 ? void 0 : trustedDeviceOption.encryptedUserKey;
            if (!deviceKey || !encDevicePrivateKey || !encUserKey) {
                if (!deviceKey) {
                    this.logService.warning("Unable to set user key due to missing device key.");
                }
                else if (!encDevicePrivateKey || !encUserKey) {
                    // Tell the server that we have a device key, but received no decryption keys
                    yield this.deviceTrustService.recordDeviceTrustLoss();
                }
                if (!encDevicePrivateKey) {
                    this.logService.warning("Unable to set user key due to missing encrypted device private key.");
                }
                if (!encUserKey) {
                    this.logService.warning("Unable to set user key due to missing encrypted user key.");
                }
                return;
            }
            const userKey = yield this.deviceTrustService.decryptUserKeyWithDeviceKey(userId, encDevicePrivateKey, encUserKey, deviceKey);
            if (userKey) {
                yield this.keyService.setUserKey(userKey, userId);
            }
        });
    }
    trySetUserKeyWithMasterKey(userId) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            // There is a scenario in which the master key is not set here. That will occur if the user
            // has a master password and is using Key Connector. In that case, we cannot set the master key
            // because the user hasn't entered their master password yet.
            // Instead, we'll return here and let the migration to Key Connector handle setting the master key.
            if (!masterKey) {
                return;
            }
            const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId);
            yield this.keyService.setUserKey(userKey, userId);
        });
    }
    setPrivateKey(tokenResponse, userId) {
        return bw_sso_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            const newSsoUser = tokenResponse.key == null;
            if (!newSsoUser) {
                yield this.keyService.setPrivateKey((_a = tokenResponse.privateKey) !== null && _a !== void 0 ? _a : (yield this.createKeyPairForOldAccount(userId)), userId);
            }
        });
    }
    exportCache() {
        return {
            sso: this.cache.value,
        };
    }
}

;// ../../libs/common/src/auth/models/request/identity-token/user-api-token.request.ts



class bw_UserApiTokenRequest extends bw_TokenRequest {
    constructor(clientId, clientSecret, twoFactor, device) {
        super(twoFactor, device);
        this.clientId = clientId;
        this.clientSecret = clientSecret;
        this.twoFactor = twoFactor;
    }
    toIdentityToken() {
        const obj = super.toIdentityToken(this.clientId);
        obj.scope = this.clientId.startsWith("organization") ? "api.organization" : "api";
        obj.grant_type = "client_credentials";
        obj.client_secret = this.clientSecret;
        return obj;
    }
    static fromJSON(json) {
        return Object.assign(Object.create(bw_UserApiTokenRequest.prototype), json, {
            device: json.device ? bw_DeviceRequest.fromJSON(json.device) : undefined,
            twoFactor: json.twoFactor
                ? Object.assign(new bw_TokenTwoFactorRequest(), json.twoFactor)
                : undefined,
        });
    }
}

;// ../../libs/auth/src/common/login-strategies/user-api-login.strategy.ts
var bw_user_api_login_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_UserApiLoginStrategyData {
    static fromJSON(obj) {
        return Object.assign(new bw_UserApiLoginStrategyData(), obj, {
            tokenRequest: bw_UserApiTokenRequest.fromJSON(obj.tokenRequest),
        });
    }
}
class bw_UserApiLoginStrategy extends bw_LoginStrategy {
    constructor(data, keyConnectorService, ...sharedDeps) {
        super(...sharedDeps);
        this.keyConnectorService = keyConnectorService;
        this.cache = new bw_external_rxjs_namespaceObject.BehaviorSubject(data);
    }
    logIn(credentials) {
        return bw_user_api_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = new bw_UserApiLoginStrategyData();
            data.tokenRequest = new bw_UserApiTokenRequest(credentials.clientId, credentials.clientSecret, yield this.buildTwoFactor(), yield this.buildDeviceRequest());
            this.cache.next(data);
            const [authResult] = yield this.startLogIn();
            return authResult;
        });
    }
    setMasterKey(response, userId) {
        return bw_user_api_login_strategy_awaiter(this, void 0, void 0, function* () {
            if (response.apiUseKeyConnector) {
                const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
                const keyConnectorUrl = env.getKeyConnectorUrl();
                yield this.keyConnectorService.setMasterKeyFromUrl(keyConnectorUrl, userId);
            }
        });
    }
    setUserKey(response, userId) {
        return bw_user_api_login_strategy_awaiter(this, void 0, void 0, function* () {
            yield this.keyService.setMasterKeyEncryptedUserKey(response.key, userId);
            if (response.apiUseKeyConnector) {
                const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
                if (masterKey) {
                    const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId);
                    yield this.keyService.setUserKey(userKey, userId);
                }
            }
        });
    }
    setPrivateKey(response, userId) {
        return bw_user_api_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            yield this.keyService.setPrivateKey((_a = response.privateKey) !== null && _a !== void 0 ? _a : (yield this.createKeyPairForOldAccount(userId)), userId);
        });
    }
    // Overridden to save client ID and secret to token service
    saveAccountInformation(tokenResponse) {
        const _super = Object.create(null, {
            saveAccountInformation: { get: () => super.saveAccountInformation }
        });
        return bw_user_api_login_strategy_awaiter(this, void 0, void 0, function* () {
            const userId = yield _super.saveAccountInformation.call(this, tokenResponse);
            const vaultTimeoutAction = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutActionByUserId$(userId));
            const vaultTimeout = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutByUserId$(userId));
            const tokenRequest = this.cache.value.tokenRequest;
            yield this.tokenService.setClientId(tokenRequest.clientId, vaultTimeoutAction, vaultTimeout);
            yield this.tokenService.setClientSecret(tokenRequest.clientSecret, vaultTimeoutAction, vaultTimeout);
            return userId;
        });
    }
    exportCache() {
        return {
            userApiKey: this.cache.value,
        };
    }
}

;// ../../libs/common/src/auth/models/request/identity-token/webauthn-login-token.request.ts




class bw_WebAuthnLoginTokenRequest extends bw_TokenRequest {
    constructor(token, deviceResponse, device) {
        super(undefined, device);
        this.token = token;
        this.deviceResponse = deviceResponse;
    }
    toIdentityToken(clientId) {
        const obj = super.toIdentityToken(clientId);
        obj.grant_type = "webauthn";
        obj.token = this.token;
        // must be a string b/c sending as form encoded data
        obj.deviceResponse = JSON.stringify(this.deviceResponse);
        return obj;
    }
    static fromJSON(json) {
        return Object.assign(Object.create(bw_WebAuthnLoginTokenRequest.prototype), json, {
            deviceResponse: bw_WebAuthnLoginAssertionResponseRequest.fromJSON(json.deviceResponse),
            device: json.device ? bw_DeviceRequest.fromJSON(json.device) : undefined,
            twoFactor: json.twoFactor
                ? Object.assign(new bw_TokenTwoFactorRequest(), json.twoFactor)
                : undefined,
        });
    }
}

;// ../../libs/auth/src/common/login-strategies/webauthn-login.strategy.ts
var bw_webauthn_login_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






class bw_WebAuthnLoginStrategyData {
    static fromJSON(obj) {
        return Object.assign(new bw_WebAuthnLoginStrategyData(), obj, {
            tokenRequest: bw_WebAuthnLoginTokenRequest.fromJSON(obj.tokenRequest),
            credentials: bw_WebAuthnLoginCredentials.fromJSON(obj.credentials),
        });
    }
}
class bw_WebAuthnLoginStrategy extends bw_LoginStrategy {
    constructor(data, ...sharedDeps) {
        super(...sharedDeps);
        this.cache = new bw_external_rxjs_namespaceObject.BehaviorSubject(data);
    }
    logIn(credentials) {
        return bw_webauthn_login_strategy_awaiter(this, void 0, void 0, function* () {
            const data = new bw_WebAuthnLoginStrategyData();
            data.credentials = credentials;
            data.tokenRequest = new bw_WebAuthnLoginTokenRequest(credentials.token, credentials.deviceResponse, yield this.buildDeviceRequest());
            this.cache.next(data);
            const [authResult] = yield this.startLogIn();
            return authResult;
        });
    }
    logInTwoFactor() {
        return bw_webauthn_login_strategy_awaiter(this, void 0, void 0, function* () {
            throw new Error("2FA not supported yet for WebAuthn Login.");
        });
    }
    setMasterKey(response, userId) {
        return bw_webauthn_login_strategy_awaiter(this, void 0, void 0, function* () {
            return Promise.resolve();
        });
    }
    setUserKey(idTokenResponse, userId) {
        return bw_webauthn_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            const masterKeyEncryptedUserKey = idTokenResponse.key;
            if (masterKeyEncryptedUserKey) {
                // set the master key encrypted user key if it exists
                yield this.keyService.setMasterKeyEncryptedUserKey(masterKeyEncryptedUserKey, userId);
            }
            const userDecryptionOptions = idTokenResponse === null || idTokenResponse === void 0 ? void 0 : idTokenResponse.userDecryptionOptions;
            if (userDecryptionOptions === null || userDecryptionOptions === void 0 ? void 0 : userDecryptionOptions.webAuthnPrfOption) {
                const webAuthnPrfOption = (_a = idTokenResponse.userDecryptionOptions) === null || _a === void 0 ? void 0 : _a.webAuthnPrfOption;
                const credentials = this.cache.value.credentials;
                // confirm we still have the prf key
                if (!credentials.prfKey) {
                    return;
                }
                // decrypt prf encrypted private key
                const privateKey = yield this.encryptService.decryptToBytes(webAuthnPrfOption.encryptedPrivateKey, credentials.prfKey);
                // decrypt user key with private key
                const userKey = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(webAuthnPrfOption.encryptedUserKey.encryptedString), privateKey);
                if (userKey) {
                    yield this.keyService.setUserKey(new bw_SymmetricCryptoKey(userKey), userId);
                }
            }
        });
    }
    setPrivateKey(response, userId) {
        return bw_webauthn_login_strategy_awaiter(this, void 0, void 0, function* () {
            var _a;
            yield this.keyService.setPrivateKey((_a = response.privateKey) !== null && _a !== void 0 ? _a : (yield this.createKeyPairForOldAccount(userId)), userId);
        });
    }
    exportCache() {
        return {
            webAuthn: this.cache.value,
        };
    }
}

;// ../../libs/auth/src/common/services/login-strategies/login-strategy.state.ts






/**
 * The current login strategy in use.
 */
const bw_CURRENT_LOGIN_STRATEGY_KEY = new bw_KeyDefinition(bw_LOGIN_STRATEGY_MEMORY, "currentLoginStrategy", {
    deserializer: (data) => data,
});
/**
 * The expiration date for the login strategy cache.
 * Used as a backup to the timer set on the service.
 */
const bw_CACHE_EXPIRATION_KEY = new bw_KeyDefinition(bw_LOGIN_STRATEGY_MEMORY, "loginStrategyCacheExpiration", {
    deserializer: (data) => (data ? null : new Date(data)),
});
/**
 * Auth Request notification for all instances of the login strategy service.
 * Note: this isn't an ideal approach, but allows both a background and
 * foreground instance to send out the notification.
 * TODO: Move to Auth Request service.
 */
const bw_AUTH_REQUEST_PUSH_NOTIFICATION_KEY = new bw_KeyDefinition(bw_LOGIN_STRATEGY_MEMORY, "authRequestPushNotification", {
    deserializer: (data) => data,
});
/**
 * A cache for login strategies to use for data persistence through
 * the login process.
 */
const bw_CACHE_KEY = new bw_KeyDefinition(bw_LOGIN_STRATEGY_MEMORY, "loginStrategyCache", {
    deserializer: (data) => {
        if (data == null) {
            return null;
        }
        return {
            password: data.password ? bw_PasswordLoginStrategyData.fromJSON(data.password) : undefined,
            sso: data.sso ? bw_SsoLoginStrategyData.fromJSON(data.sso) : undefined,
            userApiKey: data.userApiKey
                ? bw_UserApiLoginStrategyData.fromJSON(data.userApiKey)
                : undefined,
            authRequest: data.authRequest
                ? bw_AuthRequestLoginStrategyData.fromJSON(data.authRequest)
                : undefined,
            webAuthn: data.webAuthn ? bw_WebAuthnLoginStrategyData.fromJSON(data.webAuthn) : undefined,
        };
    },
});

;// ../../libs/auth/src/common/services/login-strategies/login-strategy.service.ts
var bw_login_strategy_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};












const bw_sessionTimeoutLength = 5 * 60 * 1000; // 5 minutes
class bw_LoginStrategyService {
    constructor(accountService, masterPasswordService, keyService, apiService, tokenService, appIdService, platformUtilsService, messagingService, logService, keyConnectorService, environmentService, stateService, twoFactorService, i18nService, encryptService, passwordStrengthService, policyService, deviceTrustService, authRequestService, userDecryptionOptionsService, stateProvider, billingAccountProfileStateService, vaultTimeoutSettingsService, kdfConfigService, taskSchedulerService) {
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.keyService = keyService;
        this.apiService = apiService;
        this.tokenService = tokenService;
        this.appIdService = appIdService;
        this.platformUtilsService = platformUtilsService;
        this.messagingService = messagingService;
        this.logService = logService;
        this.keyConnectorService = keyConnectorService;
        this.environmentService = environmentService;
        this.stateService = stateService;
        this.twoFactorService = twoFactorService;
        this.i18nService = i18nService;
        this.encryptService = encryptService;
        this.passwordStrengthService = passwordStrengthService;
        this.policyService = policyService;
        this.deviceTrustService = deviceTrustService;
        this.authRequestService = authRequestService;
        this.userDecryptionOptionsService = userDecryptionOptionsService;
        this.stateProvider = stateProvider;
        this.billingAccountProfileStateService = billingAccountProfileStateService;
        this.vaultTimeoutSettingsService = vaultTimeoutSettingsService;
        this.kdfConfigService = kdfConfigService;
        this.taskSchedulerService = taskSchedulerService;
        this.authenticationTimeoutSubject = new bw_external_rxjs_namespaceObject.BehaviorSubject(false);
        this.authenticationSessionTimeout$ = this.authenticationTimeoutSubject.asObservable();
        this.currentAuthnTypeState = this.stateProvider.get(bw_CURRENT_LOGIN_STRATEGY_KEY);
        this.loginStrategyCacheState = this.stateProvider.get(bw_CACHE_KEY);
        this.loginStrategyCacheExpirationState = this.stateProvider.get(bw_CACHE_EXPIRATION_KEY);
        this.authRequestPushNotificationState = this.stateProvider.get(bw_AUTH_REQUEST_PUSH_NOTIFICATION_KEY);
        this.taskSchedulerService.registerTaskHandler(bw_ScheduledTaskNames.loginStrategySessionTimeout, () => bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            this.authenticationTimeoutSubject.next(true);
            try {
                yield this.clearCache();
            }
            catch (e) {
                this.logService.error("Failed to clear cache during session timeout", e);
            }
        }));
        this.currentAuthType$ = this.currentAuthnTypeState.state$;
        this.loginStrategy$ = this.currentAuthnTypeState.state$.pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(), (0,bw_external_rxjs_namespaceObject.combineLatestWith)(this.loginStrategyCacheState.state$), this.initializeLoginStrategy.bind(this), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
    }
    getEmail() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy && "email$" in strategy) {
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(strategy.email$);
            }
            return null;
        });
    }
    getMasterPasswordHash() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy && "serverMasterKeyHash$" in strategy) {
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(strategy.serverMasterKeyHash$);
            }
            return null;
        });
    }
    getSsoEmail2FaSessionToken() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy && "ssoEmail2FaSessionToken$" in strategy) {
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(strategy.ssoEmail2FaSessionToken$);
            }
            return null;
        });
    }
    getAccessCode() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy && "accessCode$" in strategy) {
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(strategy.accessCode$);
            }
            return null;
        });
    }
    getAuthRequestId() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy && "authRequestId$" in strategy) {
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(strategy.authRequestId$);
            }
            return null;
        });
    }
    logIn(credentials) {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            yield this.clearCache();
            this.authenticationTimeoutSubject.next(false);
            yield this.currentAuthnTypeState.update((_) => credentials.type);
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            // Note: We aren't passing the credentials directly to the strategy since they are
            // created in the popup and can cause DeadObject references on Firefox.
            // This is a shallow copy, but use deep copy in future if objects are added to credentials
            // that were created in popup.
            // If the popup uses its own instance of this service, this can be removed.
            const ownedCredentials = Object.assign({}, credentials);
            const result = yield (strategy === null || strategy === void 0 ? void 0 : strategy.logIn(ownedCredentials));
            if (result != null && !result.requiresTwoFactor && !result.requiresDeviceVerification) {
                yield this.clearCache();
            }
            else {
                // Cache the strategy data so we can attempt again later with 2fa or device verification
                yield this.loginStrategyCacheState.update((_) => { var _a; return (_a = strategy === null || strategy === void 0 ? void 0 : strategy.exportCache()) !== null && _a !== void 0 ? _a : null; });
                yield this.startSessionTimeout();
            }
            if (!result) {
                throw new Error("No auth result returned");
            }
            return result;
        });
    }
    logInTwoFactor(twoFactor, captchaResponse) {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            if (!(yield this.isSessionValid())) {
                throw new Error(this.i18nService.t("sessionTimeout"));
            }
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy == null) {
                throw new Error("No login strategy found.");
            }
            try {
                const result = yield strategy.logInTwoFactor(twoFactor, captchaResponse);
                // Only clear cache if 2FA token has been accepted, otherwise we need to be able to try again
                if (result != null && !result.requiresTwoFactor && !result.requiresCaptcha) {
                    yield this.clearCache();
                }
                return result;
            }
            catch (e) {
                // API exceptions are okay, but if there are any unhandled client-side errors then clear cache to be safe
                if (!(e instanceof bw_ErrorResponse)) {
                    yield this.clearCache();
                }
                throw e;
            }
        });
    }
    /**
     * Sends a token request to the server with the provided device verification OTP.
     * Returns an error if no session data is found or if the current login strategy does not support device verification.
     * @param deviceVerificationOtp The OTP to send to the server for device verification.
     * @returns The result of the token request.
     */
    logInNewDeviceVerification(deviceVerificationOtp) {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            if (!(yield this.isSessionValid())) {
                throw new Error(this.i18nService.t("sessionTimeout"));
            }
            const strategy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategy$);
            if (strategy == null) {
                throw new Error("No login strategy found.");
            }
            if (!("logInNewDeviceVerification" in strategy)) {
                throw new Error("Current login strategy does not support device verification.");
            }
            try {
                const result = yield strategy.logInNewDeviceVerification(deviceVerificationOtp);
                // Only clear cache if device verification succeeds
                if (result !== null && !result.requiresDeviceVerification) {
                    yield this.clearCache();
                }
                return result;
            }
            catch (e) {
                // Clear the cache if there is an unhandled client-side error
                if (!(e instanceof bw_ErrorResponse)) {
                    yield this.clearCache();
                }
                throw e;
            }
        });
    }
    makePreloginKey(masterPassword, email) {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            email = email.trim().toLowerCase();
            let kdfConfig;
            try {
                const preloginResponse = yield this.apiService.postPrelogin(new bw_PreloginRequest(email));
                if (preloginResponse != null) {
                    kdfConfig =
                        preloginResponse.kdf === bw_KdfType.PBKDF2_SHA256
                            ? new bw_PBKDF2KdfConfig(preloginResponse.kdfIterations)
                            : new bw_Argon2KdfConfig(preloginResponse.kdfIterations, preloginResponse.kdfMemory, preloginResponse.kdfParallelism);
                }
            }
            catch (e) {
                if (e == null || e.statusCode !== 404) {
                    throw e;
                }
            }
            if (!kdfConfig) {
                throw new Error("KDF config is required");
            }
            kdfConfig.validateKdfConfigForPrelogin();
            return yield this.keyService.makeMasterKey(masterPassword, email, kdfConfig);
        });
    }
    clearCache() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            yield this.currentAuthnTypeState.update((_) => null);
            yield this.loginStrategyCacheState.update((_) => null);
            this.authenticationTimeoutSubject.next(false);
            yield this.clearSessionTimeout();
        });
    }
    startSessionTimeout() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            yield this.clearSessionTimeout();
            // This Login Strategy Cache Expiration State value set here is used to clear the cache on re-init
            // of the application in the case where the timeout is terminated due to a closure of the application
            // window. The browser extension popup in particular is susceptible to this concern, as the user
            // is almost always likely to close the popup window before the session timeout is reached.
            yield this.loginStrategyCacheExpirationState.update((_) => new Date(Date.now() + bw_sessionTimeoutLength));
            this.sessionTimeoutSubscription = this.taskSchedulerService.setTimeout(bw_ScheduledTaskNames.loginStrategySessionTimeout, bw_sessionTimeoutLength);
        });
    }
    clearSessionTimeout() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            yield this.loginStrategyCacheExpirationState.update((_) => null);
            (_a = this.sessionTimeoutSubscription) === null || _a === void 0 ? void 0 : _a.unsubscribe();
        });
    }
    isSessionValid() {
        return bw_login_strategy_service_awaiter(this, void 0, void 0, function* () {
            const cache = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategyCacheState.state$);
            if (cache == null) {
                return false;
            }
            // If the Login Strategy Cache Expiration State value is less than the current
            // datetime stamp, then the cache is invalid and should be cleared.
            const expiration = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.loginStrategyCacheExpirationState.state$);
            if (expiration != null && expiration < new Date()) {
                yield this.clearCache();
                return false;
            }
            return true;
        });
    }
    initializeLoginStrategy(source) {
        const sharedDeps = [
            this.accountService,
            this.masterPasswordService,
            this.keyService,
            this.encryptService,
            this.apiService,
            this.tokenService,
            this.appIdService,
            this.platformUtilsService,
            this.messagingService,
            this.logService,
            this.stateService,
            this.twoFactorService,
            this.userDecryptionOptionsService,
            this.billingAccountProfileStateService,
            this.vaultTimeoutSettingsService,
            this.kdfConfigService,
            this.environmentService,
        ];
        return source.pipe((0,bw_external_rxjs_namespaceObject.map)(([strategy, data]) => {
            var _a, _b, _c, _d, _e;
            if (strategy == null) {
                return null;
            }
            switch (strategy) {
                case bw_AuthenticationType.Password:
                    return new bw_PasswordLoginStrategy((_a = data === null || data === void 0 ? void 0 : data.password) !== null && _a !== void 0 ? _a : new bw_PasswordLoginStrategyData(), this.passwordStrengthService, this.policyService, this, ...sharedDeps);
                case bw_AuthenticationType.Sso:
                    return new bw_SsoLoginStrategy((_b = data === null || data === void 0 ? void 0 : data.sso) !== null && _b !== void 0 ? _b : new bw_SsoLoginStrategyData(), this.keyConnectorService, this.deviceTrustService, this.authRequestService, this.i18nService, ...sharedDeps);
                case bw_AuthenticationType.UserApiKey:
                    return new bw_UserApiLoginStrategy((_c = data === null || data === void 0 ? void 0 : data.userApiKey) !== null && _c !== void 0 ? _c : new bw_UserApiLoginStrategyData(), this.keyConnectorService, ...sharedDeps);
                case bw_AuthenticationType.AuthRequest:
                    return new bw_AuthRequestLoginStrategy((_d = data === null || data === void 0 ? void 0 : data.authRequest) !== null && _d !== void 0 ? _d : new bw_AuthRequestLoginStrategyData(), this.deviceTrustService, ...sharedDeps);
                case bw_AuthenticationType.WebAuthn:
                    return new bw_WebAuthnLoginStrategy((_e = data === null || data === void 0 ? void 0 : data.webAuthn) !== null && _e !== void 0 ? _e : new bw_WebAuthnLoginStrategyData(), ...sharedDeps);
            }
        }));
    }
}

;// ../../libs/auth/src/common/services/user-decryption-options/user-decryption-options.service.ts
var bw_user_decryption_options_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



const bw_USER_DECRYPTION_OPTIONS = new bw_UserKeyDefinition(bw_USER_DECRYPTION_OPTIONS_DISK, "decryptionOptions", {
    deserializer: (decryptionOptions) => bw_UserDecryptionOptions.fromJSON(decryptionOptions),
    clearOn: ["logout"],
});
class bw_UserDecryptionOptionsService {
    constructor(stateProvider) {
        this.stateProvider = stateProvider;
        this.userDecryptionOptionsState = this.stateProvider.getActive(bw_USER_DECRYPTION_OPTIONS);
        this.userDecryptionOptions$ = this.userDecryptionOptionsState.state$;
        this.hasMasterPassword$ = this.userDecryptionOptions$.pipe((0,bw_external_rxjs_namespaceObject.map)((options) => { var _a; return (_a = options === null || options === void 0 ? void 0 : options.hasMasterPassword) !== null && _a !== void 0 ? _a : false; }));
    }
    userDecryptionOptionsById$(userId) {
        return this.stateProvider.getUser(userId, bw_USER_DECRYPTION_OPTIONS).state$;
    }
    setUserDecryptionOptions(userDecryptionOptions) {
        return bw_user_decryption_options_service_awaiter(this, void 0, void 0, function* () {
            yield this.userDecryptionOptionsState.update((_) => userDecryptionOptions);
        });
    }
}

;// ../../libs/common/src/auth/models/domain/admin-auth-req-storable.ts

class bw_AdminAuthRequestStorable {
    constructor(init) {
        if (init) {
            Object.assign(this, init);
        }
    }
    toJSON() {
        return {
            id: this.id,
            privateKey: bw_utils_Utils.fromBufferToByteString(this.privateKey),
        };
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        let privateKeyBuffer = null;
        if (obj.privateKey) {
            privateKeyBuffer = bw_utils_Utils.fromByteStringToArray(obj.privateKey);
        }
        return new bw_AdminAuthRequestStorable({
            id: obj.id,
            privateKey: privateKeyBuffer,
        });
    }
}

;// ../../libs/common/src/auth/models/request/passwordless-auth.request.ts
class bw_PasswordlessAuthRequest {
    constructor(key, masterPasswordHash, deviceIdentifier, requestApproved) {
        this.key = key;
        this.masterPasswordHash = masterPasswordHash;
        this.deviceIdentifier = deviceIdentifier;
        this.requestApproved = requestApproved;
    }
}

;// ../../libs/auth/src/common/services/auth-request/auth-request.service.ts
var bw_auth_request_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







/**
 * Disk-local to maintain consistency between tabs. We don't want to
 * clear this on logout since admin auth requests are long-lived.
 */
const bw_ADMIN_AUTH_REQUEST_KEY = new bw_UserKeyDefinition(bw_AUTH_REQUEST_DISK_LOCAL, "adminAuthRequest", {
    deserializer: (value) => value,
    clearOn: [],
});
class bw_AuthRequestService {
    constructor(appIdService, accountService, masterPasswordService, keyService, encryptService, apiService, stateProvider) {
        this.appIdService = appIdService;
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.apiService = apiService;
        this.stateProvider = stateProvider;
        this.authRequestPushNotificationSubject = new bw_external_rxjs_namespaceObject.Subject();
        // Observable emission is used to trigger a toast in consuming components
        this.adminLoginApprovedSubject = new bw_external_rxjs_namespaceObject.Subject();
        this.authRequestPushNotification$ = this.authRequestPushNotificationSubject.asObservable();
        this.adminLoginApproved$ = this.adminLoginApprovedSubject.asObservable();
    }
    getAdminAuthRequest(userId) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required");
            }
            const authRequestSerialized = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_ADMIN_AUTH_REQUEST_KEY).state$);
            const adminAuthRequestStorable = bw_AdminAuthRequestStorable.fromJSON(authRequestSerialized);
            return adminAuthRequestStorable;
        });
    }
    setAdminAuthRequest(authRequest, userId) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required");
            }
            if (authRequest == null) {
                throw new Error("Auth request is required");
            }
            yield this.stateProvider.setUserState(bw_ADMIN_AUTH_REQUEST_KEY, authRequest.toJSON(), userId);
        });
    }
    clearAdminAuthRequest(userId) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required");
            }
            yield this.stateProvider.setUserState(bw_ADMIN_AUTH_REQUEST_KEY, null, userId);
        });
    }
    approveOrDenyAuthRequest(approve, authRequest) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            if (!authRequest.id) {
                throw new Error("Auth request has no id");
            }
            if (!authRequest.publicKey) {
                throw new Error("Auth request has no public key");
            }
            const pubKey = bw_utils_Utils.fromB64ToArray(authRequest.publicKey);
            const userId = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$)).id;
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            const masterKeyHash = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKeyHash$(userId));
            let encryptedMasterKeyHash;
            let keyToEncrypt;
            if (masterKey && masterKeyHash) {
                // Only encrypt the master password hash if masterKey exists as
                // we won't have a masterKeyHash without a masterKey
                encryptedMasterKeyHash = yield this.encryptService.rsaEncrypt(bw_utils_Utils.fromUtf8ToArray(masterKeyHash), pubKey);
                keyToEncrypt = masterKey.encKey;
            }
            else {
                const userKey = yield this.keyService.getUserKey();
                keyToEncrypt = userKey.key;
            }
            const encryptedKey = yield this.encryptService.rsaEncrypt(keyToEncrypt, pubKey);
            const response = new bw_PasswordlessAuthRequest(encryptedKey.encryptedString, encryptedMasterKeyHash === null || encryptedMasterKeyHash === void 0 ? void 0 : encryptedMasterKeyHash.encryptedString, yield this.appIdService.getAppId(), approve);
            return yield this.apiService.putAuthRequest(authRequest.id, response);
        });
    }
    setUserKeyAfterDecryptingSharedUserKey(authReqResponse, authReqPrivateKey, userId) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const userKey = yield this.decryptPubKeyEncryptedUserKey(authReqResponse.key, authReqPrivateKey);
            yield this.keyService.setUserKey(userKey, userId);
        });
    }
    setKeysAfterDecryptingSharedMasterKeyAndHash(authReqResponse, authReqPrivateKey, userId) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const { masterKey, masterKeyHash } = yield this.decryptPubKeyEncryptedMasterKeyAndHash(authReqResponse.key, authReqResponse.masterPasswordHash, authReqPrivateKey);
            // Decrypt and set user key in state
            const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId);
            // Set masterKey + masterKeyHash in state after decryption (in case decryption fails)
            yield this.masterPasswordService.setMasterKey(masterKey, userId);
            yield this.masterPasswordService.setMasterKeyHash(masterKeyHash, userId);
            yield this.keyService.setUserKey(userKey, userId);
        });
    }
    // Decryption helpers
    decryptPubKeyEncryptedUserKey(pubKeyEncryptedUserKey, privateKey) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const decryptedUserKeyBytes = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(pubKeyEncryptedUserKey), privateKey);
            return new bw_SymmetricCryptoKey(decryptedUserKeyBytes);
        });
    }
    decryptPubKeyEncryptedMasterKeyAndHash(pubKeyEncryptedMasterKey, pubKeyEncryptedMasterKeyHash, privateKey) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const decryptedMasterKeyArrayBuffer = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(pubKeyEncryptedMasterKey), privateKey);
            const decryptedMasterKeyHashArrayBuffer = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(pubKeyEncryptedMasterKeyHash), privateKey);
            const masterKey = new bw_SymmetricCryptoKey(decryptedMasterKeyArrayBuffer);
            const masterKeyHash = bw_utils_Utils.fromBufferToUtf8(decryptedMasterKeyHashArrayBuffer);
            return {
                masterKey,
                masterKeyHash,
            };
        });
    }
    sendAuthRequestPushNotification(notification) {
        if (notification.id != null) {
            this.authRequestPushNotificationSubject.next(notification.id);
        }
    }
    getFingerprintPhrase(email, publicKey) {
        return bw_auth_request_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.keyService.getFingerprint(email.toLowerCase(), publicKey)).join("-");
        });
    }
    emitAdminLoginApproved() {
        this.adminLoginApprovedSubject.next();
    }
}

;// ../../libs/common/src/auth/models/response/auth-request.response.ts

const bw_RequestTimeOut = 60000 * 15; //15 Minutes
class bw_auth_request_response_AuthRequestResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.publicKey = this.getResponseProperty("PublicKey");
        this.requestDeviceType = this.getResponseProperty("RequestDeviceType");
        this.requestDeviceTypeValue = this.getResponseProperty("RequestDeviceTypeValue");
        this.requestDeviceIdentifier = this.getResponseProperty("RequestDeviceIdentifier");
        this.requestIpAddress = this.getResponseProperty("RequestIpAddress");
        this.requestCountryName = this.getResponseProperty("RequestCountryName");
        this.key = this.getResponseProperty("Key");
        this.masterPasswordHash = this.getResponseProperty("MasterPasswordHash");
        this.creationDate = this.getResponseProperty("CreationDate");
        this.requestApproved = this.getResponseProperty("RequestApproved");
        this.responseDate = this.getResponseProperty("ResponseDate");
        const requestDate = new Date(this.creationDate);
        const requestDateUTC = Date.UTC(requestDate.getUTCFullYear(), requestDate.getUTCMonth(), requestDate.getDate(), requestDate.getUTCHours(), requestDate.getUTCMinutes(), requestDate.getUTCSeconds(), requestDate.getUTCMilliseconds());
        const dateNow = new Date(Date.now());
        const dateNowUTC = Date.UTC(dateNow.getUTCFullYear(), dateNow.getUTCMonth(), dateNow.getDate(), dateNow.getUTCHours(), dateNow.getUTCMinutes(), dateNow.getUTCSeconds(), dateNow.getUTCMilliseconds());
        this.isExpired = dateNowUTC - requestDateUTC >= bw_RequestTimeOut;
        this.isAnswered = this.requestApproved != null && this.responseDate != null;
    }
}

;// ../../libs/auth/src/common/services/auth-request/auth-request-api.service.ts
var bw_auth_request_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_DefaultAuthRequestApiService {
    constructor(apiService, logService) {
        this.apiService = apiService;
        this.logService = logService;
    }
    getAuthRequest(requestId) {
        return bw_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            try {
                const path = `/auth-requests/${requestId}`;
                const response = yield this.apiService.send("GET", path, null, true, true);
                return new AuthRequestResponse(response);
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    getAuthResponse(requestId, accessCode) {
        return bw_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            try {
                const path = `/auth-requests/${requestId}/response?code=${accessCode}`;
                const response = yield this.apiService.send("GET", path, null, false, true);
                return new AuthRequestResponse(response);
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    postAdminAuthRequest(request) {
        return bw_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            try {
                const response = yield this.apiService.send("POST", "/auth-requests/admin-request", request, true, true);
                return new AuthRequestResponse(response);
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    postAuthRequest(request) {
        return bw_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            try {
                // Submit the current device identifier in the header as well as in the POST body.
                // The value in the header will be used to build the request context and ensure that the resulting
                // notifications have the current device as a source.
                const response = yield this.apiService.send("POST", "/auth-requests/", request, false, true, null, (headers) => {
                    headers.set("Device-Identifier", request.deviceIdentifier);
                });
                return new AuthRequestResponse(response);
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
}

;// ../../libs/auth/src/common/services/accounts/lock.service.ts
var bw_lock_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_LockService {
}
class bw_DefaultLockService {
    constructor(accountService, vaultTimeoutService) {
        this.accountService = accountService;
        this.vaultTimeoutService = vaultTimeoutService;
    }
    lockAll() {
        return bw_lock_service_awaiter(this, void 0, void 0, function* () {
            const accounts = yield firstValueFrom(combineLatest([this.accountService.activeAccount$, this.accountService.accounts$]).pipe(map(([activeAccount, accounts]) => {
                const otherAccounts = Object.keys(accounts);
                if (activeAccount == null) {
                    return { activeAccount: null, otherAccounts: otherAccounts };
                }
                return {
                    activeAccount: activeAccount.id,
                    otherAccounts: otherAccounts.filter((accountId) => accountId !== activeAccount.id),
                };
            })));
            for (const otherAccount of accounts.otherAccounts) {
                yield this.vaultTimeoutService.lock(otherAccount);
            }
            // Do the active account last in case we ever try to route the user on lock
            // that way this whole operation will be complete before that routing
            // could take place.
            if (accounts.activeAccount != null) {
                yield this.vaultTimeoutService.lock(accounts.activeAccount);
            }
        });
    }
}

;// ../../libs/auth/src/common/services/login-success-handler/default-login-success-handler.service.ts
var bw_default_login_success_handler_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_DefaultLoginSuccessHandlerService {
    constructor(syncService, userAsymmetricKeysRegenerationService) {
        this.syncService = syncService;
        this.userAsymmetricKeysRegenerationService = userAsymmetricKeysRegenerationService;
    }
    run(userId) {
        return bw_default_login_success_handler_service_awaiter(this, void 0, void 0, function* () {
            yield this.syncService.fullSync(true);
            yield this.userAsymmetricKeysRegenerationService.regenerateIfNeeded(userId);
        });
    }
}

;// ../../libs/auth/src/common/services/sso-redirect/sso-url.service.ts
const bw_DESKTOP_SSO_CALLBACK = "bitwarden://sso-callback";
class bw_SsoUrlService {
    /**
     * Builds a URL for redirecting users to the web app SSO component to complete SSO
     * @param webAppUrl The URL of the web app
     * @param clientType The client type that is initiating SSO, which will drive how the response is handled
     * @param redirectUri The redirect URI or callback that will receive the SSO code after authentication
     * @param state A state value that will be peristed through the SSO flow
     * @param codeChallenge A challenge value that will be used to verify the SSO code after authentication
     * @param email The optional email adddress of the user initiating SSO, which will be used to look up the org SSO identifier
     * @returns The URL for redirecting users to the web app SSO component
     */
    buildSsoUrl(webAppUrl, clientType, redirectUri, state, codeChallenge, email) {
        let url = webAppUrl +
            "/#/sso?clientId=" +
            clientType +
            "&redirectUri=" +
            encodeURIComponent(redirectUri) +
            "&state=" +
            state +
            "&codeChallenge=" +
            codeChallenge;
        if (email) {
            url += "&email=" + encodeURIComponent(email);
        }
        return url;
    }
}

;// ../../libs/auth/src/common/services/index.ts










;// ../../libs/auth/src/common/utilities/decode-jwt-token-to-json.utility.ts

function bw_decodeJwtTokenToJson(jwtToken) {
    if (jwtToken == null) {
        throw new Error("JWT token not found");
    }
    const parts = jwtToken.split(".");
    if (parts.length !== 3) {
        throw new Error("JWT must have 3 parts");
    }
    // JWT has 3 parts: header, payload, signature separated by '.'
    // So, grab the payload to decode
    const encodedPayload = parts[1];
    let decodedPayloadJSON;
    try {
        // Attempt to decode from URL-safe Base64 to UTF-8
        decodedPayloadJSON = bw_utils_Utils.fromUrlB64ToUtf8(encodedPayload);
        // FIXME: Remove when updating file. Eslint update
        // eslint-disable-next-line @typescript-eslint/no-unused-vars
    }
    catch (decodingError) {
        throw new Error("Cannot decode the token");
    }
    try {
        // Attempt to parse the JSON payload
        const decodedToken = JSON.parse(decodedPayloadJSON);
        return decodedToken;
        // FIXME: Remove when updating file. Eslint update
        // eslint-disable-next-line @typescript-eslint/no-unused-vars
    }
    catch (jsonError) {
        throw new Error("Cannot parse the token's payload into JSON");
    }
}

;// ../../libs/auth/src/common/utilities/index.ts


;// ../../libs/auth/src/common/login-strategies/index.ts


;// ../../libs/auth/src/common/index.ts
/**
 * This barrel file should only contain non-Angular exports
 */







;// ../../libs/common/src/auth/models/request/secret-verification.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_SecretVerificationRequest {
}

;// ../../libs/common/src/auth/models/request/password.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_PasswordRequest extends bw_SecretVerificationRequest {
}

;// ../../libs/common/src/auth/models/request/two-factor-email.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_TwoFactorEmailRequest extends bw_SecretVerificationRequest {
}

;// ../../libs/common/src/models/response/list.response.ts

class bw_ListResponse extends bw_BaseResponse {
    constructor(response, t) {
        super(response);
        const data = this.getResponseProperty("Data");
        this.data = data == null ? [] : data.map((dr) => new t(dr));
        this.continuationToken = this.getResponseProperty("ContinuationToken");
    }
}

;// ../../libs/admin-console/src/common/organization-user/models/requests/organization-user-bulk.request.ts
class bw_OrganizationUserBulkRequest {
    constructor(ids) {
        this.ids = ids == null ? [] : ids;
    }
}

;// ../../libs/common/src/admin-console/models/api/permissions.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_PermissionsApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return this;
        }
        this.accessEventLogs = this.getResponseProperty("AccessEventLogs");
        this.accessImportExport = this.getResponseProperty("AccessImportExport");
        this.accessReports = this.getResponseProperty("AccessReports");
        this.createNewCollections = this.getResponseProperty("CreateNewCollections");
        this.editAnyCollection = this.getResponseProperty("EditAnyCollection");
        this.deleteAnyCollection = this.getResponseProperty("DeleteAnyCollection");
        this.manageCiphers = this.getResponseProperty("ManageCiphers");
        this.manageGroups = this.getResponseProperty("ManageGroups");
        this.manageSso = this.getResponseProperty("ManageSso");
        this.managePolicies = this.getResponseProperty("ManagePolicies");
        this.manageUsers = this.getResponseProperty("ManageUsers");
        this.manageResetPassword = this.getResponseProperty("ManageResetPassword");
        this.manageScim = this.getResponseProperty("ManageScim");
    }
}

;// ../../libs/common/src/admin-console/models/response/selection-read-only.response.ts

class bw_SelectionReadOnlyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.readOnly = this.getResponseProperty("ReadOnly");
        this.hidePasswords = this.getResponseProperty("HidePasswords");
        this.manage = this.getResponseProperty("Manage");
    }
}

;// ../../libs/admin-console/src/common/organization-user/models/responses/organization-user.response.ts



class bw_OrganizationUserResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.collections = [];
        this.groups = [];
        this.id = this.getResponseProperty("Id");
        this.userId = this.getResponseProperty("UserId");
        this.type = this.getResponseProperty("Type");
        this.status = this.getResponseProperty("Status");
        this.permissions = new bw_PermissionsApi(this.getResponseProperty("Permissions"));
        this.externalId = this.getResponseProperty("ExternalId");
        this.accessSecretsManager = this.getResponseProperty("AccessSecretsManager");
        this.resetPasswordEnrolled = this.getResponseProperty("ResetPasswordEnrolled");
        this.hasMasterPassword = this.getResponseProperty("HasMasterPassword");
        const collections = this.getResponseProperty("Collections");
        if (collections != null) {
            this.collections = collections.map((c) => new bw_SelectionReadOnlyResponse(c));
        }
        const groups = this.getResponseProperty("Groups");
        if (groups != null) {
            this.groups = groups;
        }
    }
}
class bw_OrganizationUserUserDetailsResponse extends bw_OrganizationUserResponse {
    constructor(response) {
        var _a, _b;
        super(response);
        this.name = this.getResponseProperty("Name");
        this.email = this.getResponseProperty("Email");
        this.avatarColor = this.getResponseProperty("AvatarColor");
        this.twoFactorEnabled = this.getResponseProperty("TwoFactorEnabled");
        this.usesKeyConnector = (_a = this.getResponseProperty("UsesKeyConnector")) !== null && _a !== void 0 ? _a : false;
        this.managedByOrganization = (_b = this.getResponseProperty("ManagedByOrganization")) !== null && _b !== void 0 ? _b : false;
    }
}
class bw_OrganizationUserDetailsResponse extends bw_OrganizationUserResponse {
    constructor(response) {
        var _a;
        super(response);
        this.managedByOrganization = (_a = this.getResponseProperty("ManagedByOrganization")) !== null && _a !== void 0 ? _a : false;
    }
}
class bw_OrganizationUserResetPasswordDetailsResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.organizationUserId = this.getResponseProperty("OrganizationUserId");
        this.kdf = this.getResponseProperty("Kdf");
        this.kdfIterations = this.getResponseProperty("KdfIterations");
        this.kdfMemory = this.getResponseProperty("KdfMemory");
        this.kdfParallelism = this.getResponseProperty("KdfParallelism");
        this.resetPasswordKey = this.getResponseProperty("ResetPasswordKey");
        this.encryptedPrivateKey = this.getResponseProperty("EncryptedPrivateKey");
    }
}

;// ../../libs/admin-console/src/common/organization-user/models/responses/organization-user-bulk.response.ts

class bw_OrganizationUserBulkResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.error = this.getResponseProperty("Error");
    }
}

;// ../../libs/admin-console/src/common/organization-user/models/responses/organization-user-bulk-public-key.response.ts

class bw_OrganizationUserBulkPublicKeyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.userId = this.getResponseProperty("UserId");
        this.key = this.getResponseProperty("Key");
    }
}

;// ../../libs/admin-console/src/common/organization-user/models/responses/organization-user-mini.response.ts

class bw_OrganizationUserUserMiniResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.userId = this.getResponseProperty("UserId");
        this.email = this.getResponseProperty("Email");
        this.name = this.getResponseProperty("Name");
        this.type = this.getResponseProperty("Type");
        this.status = this.getResponseProperty("Status");
    }
}

;// ../../libs/admin-console/src/common/organization-user/models/responses/index.ts





;// ../../libs/admin-console/src/common/organization-user/services/default-organization-user-api.service.ts
var bw_default_organization_user_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_DefaultOrganizationUserApiService {
    constructor(apiService) {
        this.apiService = apiService;
    }
    getOrganizationUser(organizationId, id, options) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const params = new URLSearchParams();
            if (options === null || options === void 0 ? void 0 : options.includeGroups) {
                params.set("includeGroups", "true");
            }
            const r = yield this.apiService.send("GET", `/organizations/${organizationId}/users/${id}?${params.toString()}`, null, true, true);
            return new bw_OrganizationUserDetailsResponse(r);
        });
    }
    getOrganizationUserGroups(organizationId, id) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + organizationId + "/users/" + id + "/groups", null, true, true);
            return r;
        });
    }
    getAllUsers(organizationId, options) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const params = new URLSearchParams();
            if (options === null || options === void 0 ? void 0 : options.includeCollections) {
                params.set("includeCollections", "true");
            }
            if (options === null || options === void 0 ? void 0 : options.includeGroups) {
                params.set("includeGroups", "true");
            }
            const r = yield this.apiService.send("GET", `/organizations/${organizationId}/users?${params.toString()}`, null, true, true);
            return new bw_ListResponse(r, bw_OrganizationUserUserDetailsResponse);
        });
    }
    getAllMiniUserDetails(organizationId) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", `/organizations/${organizationId}/users/mini-details`, null, true, true);
            return new bw_ListResponse(r, bw_OrganizationUserUserMiniResponse);
        });
    }
    getOrganizationUserResetPasswordDetails(organizationId, id) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + organizationId + "/users/" + id + "/reset-password-details", null, true, true);
            return new bw_OrganizationUserResetPasswordDetailsResponse(r);
        });
    }
    getManyOrganizationUserAccountRecoveryDetails(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + organizationId + "/users/account-recovery-details", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserResetPasswordDetailsResponse);
        });
    }
    postOrganizationUserInvite(organizationId, request) {
        return this.apiService.send("POST", "/organizations/" + organizationId + "/users/invite", request, true, false);
    }
    postOrganizationUserReinvite(organizationId, id) {
        return this.apiService.send("POST", "/organizations/" + organizationId + "/users/" + id + "/reinvite", null, true, false);
    }
    postManyOrganizationUserReinvite(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + organizationId + "/users/reinvite", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkResponse);
        });
    }
    postOrganizationUserAcceptInit(organizationId, id, request) {
        return this.apiService.send("POST", "/organizations/" + organizationId + "/users/" + id + "/accept-init", request, true, false);
    }
    postOrganizationUserAccept(organizationId, id, request) {
        return this.apiService.send("POST", "/organizations/" + organizationId + "/users/" + id + "/accept", request, true, false);
    }
    postOrganizationUserConfirm(organizationId, id, request) {
        return this.apiService.send("POST", "/organizations/" + organizationId + "/users/" + id + "/confirm", request, true, false);
    }
    postOrganizationUsersPublicKey(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + organizationId + "/users/public-keys", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkPublicKeyResponse);
        });
    }
    postOrganizationUserBulkConfirm(organizationId, request) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + organizationId + "/users/confirm", request, true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkResponse);
        });
    }
    putOrganizationUserBulkEnableSecretsManager(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("PUT", "/organizations/" + organizationId + "/users/enable-secrets-manager", new bw_OrganizationUserBulkRequest(ids), true, false);
        });
    }
    putOrganizationUser(organizationId, id, request) {
        return this.apiService.send("PUT", "/organizations/" + organizationId + "/users/" + id, request, true, false);
    }
    putOrganizationUserResetPasswordEnrollment(organizationId, userId, request) {
        return this.apiService.send("PUT", "/organizations/" + organizationId + "/users/" + userId + "/reset-password-enrollment", request, true, false);
    }
    putOrganizationUserResetPassword(organizationId, id, request) {
        return this.apiService.send("PUT", "/organizations/" + organizationId + "/users/" + id + "/reset-password", request, true, false);
    }
    removeOrganizationUser(organizationId, id) {
        return this.apiService.send("DELETE", "/organizations/" + organizationId + "/users/" + id, null, true, false);
    }
    removeManyOrganizationUsers(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("DELETE", "/organizations/" + organizationId + "/users", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkResponse);
        });
    }
    revokeOrganizationUser(organizationId, id) {
        return this.apiService.send("PUT", "/organizations/" + organizationId + "/users/" + id + "/revoke", null, true, false);
    }
    revokeManyOrganizationUsers(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/organizations/" + organizationId + "/users/revoke", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkResponse);
        });
    }
    restoreOrganizationUser(organizationId, id) {
        return this.apiService.send("PUT", "/organizations/" + organizationId + "/users/" + id + "/restore", null, true, false);
    }
    restoreManyOrganizationUsers(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/organizations/" + organizationId + "/users/restore", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkResponse);
        });
    }
    deleteOrganizationUser(organizationId, id) {
        return this.apiService.send("DELETE", "/organizations/" + organizationId + "/users/" + id + "/delete-account", null, true, false);
    }
    deleteManyOrganizationUsers(organizationId, ids) {
        return bw_default_organization_user_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("DELETE", "/organizations/" + organizationId + "/users/delete-account", new bw_OrganizationUserBulkRequest(ids), true, true);
            return new bw_ListResponse(r, bw_OrganizationUserBulkResponse);
        });
    }
}

;// ../../libs/admin-console/src/common/organization-user/services/index.ts


;// ../../libs/admin-console/src/common/organization-user/models/requests/organization-user-confirm.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_OrganizationUserConfirmRequest {
}

;// ../../libs/admin-console/src/common/organization-user/models/requests/organization-user-reset-password.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_OrganizationUserResetPasswordRequest {
}

;// ../../libs/admin-console/src/common/organization-user/models/requests/index.ts










;// ../../libs/admin-console/src/common/organization-user/models/index.ts



;// ../../libs/admin-console/src/common/organization-user/index.ts




;// ../../libs/common/src/models/view/view.ts
class bw_View {
}

;// ../../libs/admin-console/src/common/collections/models/collection-access-selection.view.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_CollectionAccessSelectionView extends bw_View {
    constructor(response) {
        super();
        if (!response) {
            return;
        }
        this.id = response.id;
        this.readOnly = response.readOnly;
        this.hidePasswords = response.hidePasswords;
        this.manage = response.manage;
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_Collection extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            id: null,
            organizationId: null,
            name: null,
            externalId: null,
            readOnly: null,
            hidePasswords: null,
            manage: null,
        }, ["id", "organizationId", "readOnly", "hidePasswords", "manage"]);
    }
    decrypt(orgKey) {
        return this.decryptObj(this, new bw_CollectionView(this), ["name"], this.organizationId, orgKey);
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection.response.ts


class bw_CollectionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.organizationId = this.getResponseProperty("OrganizationId");
        this.name = this.getResponseProperty("Name");
        this.externalId = this.getResponseProperty("ExternalId");
    }
}
class bw_CollectionDetailsResponse extends bw_CollectionResponse {
    constructor(response) {
        super(response);
        this.readOnly = this.getResponseProperty("ReadOnly") || false;
        this.manage = this.getResponseProperty("Manage") || false;
        this.hidePasswords = this.getResponseProperty("HidePasswords") || false;
        // Temporary until the API is updated to return this property in AC-2084
        // For now, we can assume that if the object is 'collectionDetails' then the user is assigned
        this.assigned = this.getResponseProperty("object") == "collectionDetails";
    }
}
class bw_CollectionAccessDetailsResponse extends bw_CollectionDetailsResponse {
    constructor(response) {
        super(response);
        this.groups = [];
        this.users = [];
        this.assigned = this.getResponseProperty("Assigned") || false;
        this.unmanaged = this.getResponseProperty("Unmanaged") || false;
        const groups = this.getResponseProperty("Groups");
        if (groups != null) {
            this.groups = groups.map((g) => new bw_SelectionReadOnlyResponse(g));
        }
        const users = this.getResponseProperty("Users");
        if (users != null) {
            this.users = users.map((g) => new bw_SelectionReadOnlyResponse(g));
        }
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection.view.ts


const bw_NestingDelimiter = "/";
class bw_CollectionView {
    constructor(c) {
        this.id = null;
        this.organizationId = null;
        this.name = null;
        this.externalId = null;
        // readOnly applies to the items within a collection
        this.readOnly = null;
        this.hidePasswords = null;
        this.manage = null;
        this.assigned = null;
        if (!c) {
            return;
        }
        this.id = c.id;
        this.organizationId = c.organizationId;
        this.externalId = c.externalId;
        if (c instanceof bw_Collection) {
            this.readOnly = c.readOnly;
            this.hidePasswords = c.hidePasswords;
            this.manage = c.manage;
            this.assigned = true;
        }
        if (c instanceof bw_CollectionAccessDetailsResponse) {
            this.assigned = c.assigned;
        }
    }
    canEditItems(org) {
        if (org != null && org.id !== this.organizationId) {
            throw new Error("Id of the organization provided does not match the org id of the collection.");
        }
        return (org === null || org === void 0 ? void 0 : org.canEditAllCiphers) || this.manage || (this.assigned && !this.readOnly);
    }
    /**
     * Returns true if the user can edit a collection (including user and group access) from the individual vault.
     * Does not include admin permissions - see {@link CollectionAdminView.canEdit}.
     */
    canEdit(org) {
        if (org != null && org.id !== this.organizationId) {
            throw new Error("Id of the organization provided does not match the org id of the collection.");
        }
        return this.manage;
    }
    /**
     * Returns true if the user can delete a collection from the individual vault.
     * Does not include admin permissions - see {@link CollectionAdminView.canDelete}.
     */
    canDelete(org) {
        if (org != null && org.id !== this.organizationId) {
            throw new Error("Id of the organization provided does not match the org id of the collection.");
        }
        const canDeleteManagedCollections = !(org === null || org === void 0 ? void 0 : org.limitCollectionDeletion) || org.isAdmin;
        // Only use individual permissions, not admin permissions
        return canDeleteManagedCollections && this.manage;
    }
    /**
     * Returns true if the user can view collection info and access in a read-only state from the individual vault
     */
    canViewCollectionInfo(org) {
        return false;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_CollectionView(new bw_Collection()), obj);
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection-admin.view.ts


const bw_Unassigned = "unassigned";
class bw_collection_admin_view_CollectionAdminView extends bw_CollectionView {
    constructor(response) {
        super(response);
        this.groups = [];
        this.users = [];
        if (!response) {
            return;
        }
        this.groups = response.groups
            ? response.groups.map((g) => new bw_CollectionAccessSelectionView(g))
            : [];
        this.users = response.users
            ? response.users.map((g) => new bw_CollectionAccessSelectionView(g))
            : [];
        this.assigned = response.assigned;
    }
    /**
     * Returns true if the user can edit a collection (including user and group access) from the Admin Console.
     */
    canEdit(org) {
        return ((org === null || org === void 0 ? void 0 : org.canEditAnyCollection) ||
            (this.unmanaged && (org === null || org === void 0 ? void 0 : org.canEditUnmanagedCollections)) ||
            super.canEdit(org));
    }
    /**
     * Returns true if the user can delete a collection from the Admin Console.
     */
    canDelete(org) {
        return (org === null || org === void 0 ? void 0 : org.canDeleteAnyCollection) || super.canDelete(org);
    }
    /**
     * Whether the user can modify user access to this collection
     */
    canEditUserAccess(org) {
        return ((org.permissions.manageUsers && org.allowAdminAccessToAllCollectionItems) || this.canEdit(org));
    }
    /**
     * Whether the user can modify group access to this collection
     */
    canEditGroupAccess(org) {
        return ((org.permissions.manageGroups && org.allowAdminAccessToAllCollectionItems) ||
            this.canEdit(org));
    }
    /**
     * Returns true if the user can view collection info and access in a read-only state from the Admin Console
     */
    canViewCollectionInfo(org) {
        if (this.isUnassignedCollection) {
            return false;
        }
        return this.manage || (org === null || org === void 0 ? void 0 : org.isAdmin) || (org === null || org === void 0 ? void 0 : org.permissions.editAnyCollection);
    }
    /**
     * True if this collection represents the pseudo "Unassigned" collection
     * This is different from the "unmanaged" flag, which indicates that no users or groups have access to the collection
     */
    get isUnassignedCollection() {
        return this.id === bw_Unassigned;
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection.data.ts

class bw_collection_data_CollectionData {
    constructor(response) {
        this.id = response.id;
        this.organizationId = response.organizationId;
        this.name = response.name;
        this.externalId = response.externalId;
        this.readOnly = response.readOnly;
        this.manage = response.manage;
        this.hidePasswords = response.hidePasswords;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_collection_data_CollectionData(new bw_CollectionDetailsResponse({})), obj);
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection.request.ts
class bw_collection_request_CollectionRequest {
    constructor(collection) {
        this.groups = [];
        this.users = [];
        if (collection == null) {
            return;
        }
        this.name = collection.name ? collection.name.encryptedString : null;
        this.externalId = collection.externalId;
    }
}

;// ../../libs/admin-console/src/common/collections/models/collection-with-id.request.ts

class bw_CollectionWithIdRequest extends bw_collection_request_CollectionRequest {
    constructor(collection) {
        if (collection == null) {
            return;
        }
        super(collection);
        this.id = collection.id;
    }
}

;// ../../libs/admin-console/src/common/collections/models/index.ts










;// ../../libs/admin-console/src/common/collections/services/default-collection-admin.service.ts
var bw_default_collection_admin_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_DefaultCollectionAdminService {
    constructor(apiService, keyService, encryptService, collectionService) {
        this.apiService = apiService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.collectionService = collectionService;
    }
    getAll(organizationId) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            const collectionResponse = yield this.apiService.getManyCollectionsWithAccessDetails(organizationId);
            if ((collectionResponse === null || collectionResponse === void 0 ? void 0 : collectionResponse.data) == null || collectionResponse.data.length === 0) {
                return [];
            }
            return yield this.decryptMany(organizationId, collectionResponse.data);
        });
    }
    get(organizationId, collectionId) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            const collectionResponse = yield this.apiService.getCollectionAccessDetails(organizationId, collectionId);
            if (collectionResponse == null) {
                return undefined;
            }
            const [view] = yield this.decryptMany(organizationId, [collectionResponse]);
            return view;
        });
    }
    save(collection) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            const request = yield this.encrypt(collection);
            let response;
            if (collection.id == null) {
                response = yield this.apiService.postCollection(collection.organizationId, request);
                collection.id = response.id;
            }
            else {
                response = yield this.apiService.putCollection(collection.organizationId, collection.id, request);
            }
            if (response.assigned) {
                yield this.collectionService.upsert(new CollectionData(response));
            }
            else {
                yield this.collectionService.delete(collection.id);
            }
            return response;
        });
    }
    delete(organizationId, collectionId) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.deleteCollection(organizationId, collectionId);
        });
    }
    bulkAssignAccess(organizationId, collectionIds, users, groups) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            const request = new BulkCollectionAccessRequest();
            request.collectionIds = collectionIds;
            request.users = users.map((u) => new SelectionReadOnlyRequest(u.id, u.readOnly, u.hidePasswords, u.manage));
            request.groups = groups.map((g) => new SelectionReadOnlyRequest(g.id, g.readOnly, g.hidePasswords, g.manage));
            yield this.apiService.send("POST", `/organizations/${organizationId}/collections/bulk-access`, request, true, false);
        });
    }
    decryptMany(organizationId, collections) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            const orgKey = yield this.keyService.getOrgKey(organizationId);
            const promises = collections.map((c) => bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
                const view = new CollectionAdminView();
                view.id = c.id;
                view.name = yield this.encryptService.decryptToUtf8(new EncString(c.name), orgKey);
                view.externalId = c.externalId;
                view.organizationId = c.organizationId;
                if (bw_isCollectionAccessDetailsResponse(c)) {
                    view.groups = c.groups;
                    view.users = c.users;
                    view.assigned = c.assigned;
                    view.readOnly = c.readOnly;
                    view.hidePasswords = c.hidePasswords;
                    view.manage = c.manage;
                    view.unmanaged = c.unmanaged;
                }
                return view;
            }));
            return yield Promise.all(promises);
        });
    }
    encrypt(model) {
        return bw_default_collection_admin_service_awaiter(this, void 0, void 0, function* () {
            if (model.organizationId == null) {
                throw new Error("Collection has no organization id.");
            }
            const key = yield this.keyService.getOrgKey(model.organizationId);
            if (key == null) {
                throw new Error("No key for this collection's organization.");
            }
            const collection = new CollectionRequest();
            collection.externalId = model.externalId;
            collection.name = (yield this.encryptService.encrypt(model.name, key)).encryptedString;
            collection.groups = model.groups.map((group) => new SelectionReadOnlyRequest(group.id, group.readOnly, group.hidePasswords, group.manage));
            collection.users = model.users.map((user) => new SelectionReadOnlyRequest(user.id, user.readOnly, user.hidePasswords, user.manage));
            return collection;
        });
    }
}
function bw_isCollectionAccessDetailsResponse(response) {
    const anyResponse = response;
    return (anyResponse === null || anyResponse === void 0 ? void 0 : anyResponse.groups) instanceof Array && (anyResponse === null || anyResponse === void 0 ? void 0 : anyResponse.users) instanceof Array;
}

;// ../../libs/common/src/vault/models/domain/tree-node.ts
class bw_TreeNode {
    constructor(node, parent, name, id) {
        this.children = [];
        this.parent = parent;
        this.node = node;
        if (name) {
            this.node.name = name;
        }
        if (id) {
            this.node.id = id;
        }
    }
}

;// ../../libs/common/src/vault/service-utils.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_ServiceUtils {
    /**
     * Recursively adds a node to nodeTree
     * @param {TreeNode<ITreeNodeObject>[]} nodeTree - An array of TreeNodes that the node will be added to
     * @param {number} partIndex - Index of the `parts` array that is being processed
     * @param {string[]} parts - Array of strings that represent the path to the `obj` node
     * @param {ITreeNodeObject} obj - The node to be added to the tree
     * @param {ITreeNodeObject} parent - The parent node of the `obj` node
     * @param {string} delimiter - The delimiter used to split the path string, will be used to combine the path for missing nodes
     */
    static nestedTraverse(nodeTree, partIndex, parts, obj, parent, delimiter) {
        if (parts.length <= partIndex) {
            return;
        }
        const end = partIndex === parts.length - 1;
        const partName = parts[partIndex];
        for (let i = 0; i < nodeTree.length; i++) {
            if (nodeTree[i].node.name !== partName) {
                continue;
            }
            if (end && nodeTree[i].node.id !== obj.id) {
                // Another node exists with the same name as the node being added
                nodeTree.push(new bw_TreeNode(obj, parent, partName));
                return;
            }
            // Move down the tree to the next level
            bw_ServiceUtils.nestedTraverse(nodeTree[i].children, partIndex + 1, parts, obj, nodeTree[i], delimiter);
            return;
        }
        // If there's no node here with the same name...
        if (nodeTree.filter((n) => n.node.name === partName).length === 0) {
            // And we're at the end of the path given, add the node
            if (end) {
                nodeTree.push(new bw_TreeNode(obj, parent, partName));
                return;
            }
            // And we're not at the end of the path, combine the current name with the next name
            // 1, *1.2, 1.2.1 becomes
            // 1, *1.2/1.2.1
            const newPartName = partName + delimiter + parts[partIndex + 1];
            bw_ServiceUtils.nestedTraverse(nodeTree, 0, [newPartName, ...parts.slice(partIndex + 2)], obj, parent, delimiter);
        }
    }
    /**
     * Searches a tree for a node with a matching `id`
     * @param {TreeNode<T>} nodeTree - A single TreeNode branch that will be searched
     * @param {string} id - The id of the node to be found
     * @returns {TreeNode<T>} The node with a matching `id`
     */
    static getTreeNodeObject(nodeTree, id) {
        if (nodeTree.node.id === id) {
            return nodeTree;
        }
        for (let i = 0; i < nodeTree.children.length; i++) {
            if (nodeTree.children[i].children != null) {
                const node = bw_ServiceUtils.getTreeNodeObject(nodeTree.children[i], id);
                if (node !== null) {
                    return node;
                }
            }
        }
        return null;
    }
    /**
     * Searches an array of tree nodes for a node with a matching `id`
     * @param {TreeNode<T>} nodeTree - An array of TreeNode branches that will be searched
     * @param {string} id - The id of the node to be found
     * @returns {TreeNode<T>} The node with a matching `id`
     */
    static getTreeNodeObjectFromList(nodeTree, id) {
        for (let i = 0; i < nodeTree.length; i++) {
            if (nodeTree[i].node.id === id) {
                return nodeTree[i];
            }
            else if (nodeTree[i].children != null) {
                const node = bw_ServiceUtils.getTreeNodeObjectFromList(nodeTree[i].children, id);
                if (node !== null) {
                    return node;
                }
            }
        }
        return null;
    }
}

;// ../../libs/admin-console/src/common/collections/services/default-collection.service.ts
var bw_default_collection_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





const bw_ENCRYPTED_COLLECTION_DATA_KEY = bw_UserKeyDefinition.record(bw_COLLECTION_DATA, "collections", {
    deserializer: (jsonData) => bw_collection_data_CollectionData.fromJSON(jsonData),
    clearOn: ["logout"],
});
const bw_DECRYPTED_COLLECTION_DATA_KEY = new bw_DeriveDefinition(bw_COLLECTION_DATA, "decryptedCollections", {
    deserializer: (obj) => obj.map((collection) => bw_CollectionView.fromJSON(collection)),
    derive: (_a, _b) => bw_default_collection_service_awaiter(void 0, [_a, _b], void 0, function* ([collections, orgKeys], { collectionService }) {
        if (collections == null) {
            return [];
        }
        const data = Object.values(collections).map((c) => new bw_Collection(c));
        return yield collectionService.decryptMany(data, orgKeys);
    }),
});
const bw_default_collection_service_NestingDelimiter = "/";
class bw_DefaultCollectionService {
    decryptedCollectionViews$(ids) {
        return this.decryptedCollections$.pipe((0,bw_external_rxjs_namespaceObject.map)((collections) => collections.filter((c) => ids.includes(c.id))));
    }
    constructor(keyService, encryptService, i18nService, stateProvider) {
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.i18nService = i18nService;
        this.stateProvider = stateProvider;
        this.encryptedCollectionDataState = this.stateProvider.getActive(bw_ENCRYPTED_COLLECTION_DATA_KEY);
        this.encryptedCollections$ = this.encryptedCollectionDataState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((collections) => {
            if (collections == null) {
                return [];
            }
            return Object.values(collections).map((c) => new bw_Collection(c));
        }));
        const encryptedCollectionsWithKeys = this.encryptedCollectionDataState.combinedState$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)(([userId, collectionData]) => (0,bw_external_rxjs_namespaceObject.combineLatest)([(0,bw_external_rxjs_namespaceObject.of)(collectionData), this.keyService.orgKeys$(userId)])));
        this.decryptedCollectionDataState = this.stateProvider.getDerived(encryptedCollectionsWithKeys, bw_DECRYPTED_COLLECTION_DATA_KEY, { collectionService: this });
        this.decryptedCollections$ = this.decryptedCollectionDataState.state$;
    }
    clearActiveUserCache() {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            yield this.decryptedCollectionDataState.forceValue(null);
        });
    }
    encrypt(model) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            if (model.organizationId == null) {
                throw new Error("Collection has no organization id.");
            }
            const key = yield this.keyService.getOrgKey(model.organizationId);
            if (key == null) {
                throw new Error("No key for this collection's organization.");
            }
            const collection = new bw_Collection();
            collection.id = model.id;
            collection.organizationId = model.organizationId;
            collection.readOnly = model.readOnly;
            collection.externalId = model.externalId;
            collection.name = yield this.encryptService.encrypt(model.name, key);
            return collection;
        });
    }
    // TODO: this should be private and orgKeys should be required.
    // See https://bitwarden.atlassian.net/browse/PM-12375
    decryptMany(collections, orgKeys) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            if (collections == null || collections.length === 0) {
                return [];
            }
            const decCollections = [];
            orgKeys !== null && orgKeys !== void 0 ? orgKeys : (orgKeys = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.activeUserOrgKeys$));
            const promises = [];
            collections.forEach((collection) => {
                promises.push(collection
                    .decrypt(orgKeys[collection.organizationId])
                    .then((c) => decCollections.push(c)));
            });
            yield Promise.all(promises);
            return decCollections.sort(bw_utils_Utils.getSortFunction(this.i18nService, "name"));
        });
    }
    get(id) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            return ((_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.encryptedCollections$.pipe((0,bw_external_rxjs_namespaceObject.map)((cs) => cs.find((c) => c.id === id)))))) !== null && _a !== void 0 ? _a : null);
        });
    }
    getAll() {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.encryptedCollections$);
        });
    }
    getAllDecrypted() {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.decryptedCollections$);
        });
    }
    getAllNested() {
        return bw_default_collection_service_awaiter(this, arguments, void 0, function* (collections = null) {
            if (collections == null) {
                collections = yield this.getAllDecrypted();
            }
            const nodes = [];
            collections.forEach((c) => {
                const collectionCopy = new bw_CollectionView();
                collectionCopy.id = c.id;
                collectionCopy.organizationId = c.organizationId;
                const parts = c.name != null ? c.name.replace(/^\/+|\/+$/g, "").split(bw_default_collection_service_NestingDelimiter) : [];
                bw_ServiceUtils.nestedTraverse(nodes, 0, parts, collectionCopy, null, bw_default_collection_service_NestingDelimiter);
            });
            return nodes;
        });
    }
    /**
     * @deprecated August 30 2022: Moved to new Vault Filter Service
     * Remove when Desktop and Browser are updated
     */
    getNested(id) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            const collections = yield this.getAllNested();
            return bw_ServiceUtils.getTreeNodeObjectFromList(collections, id);
        });
    }
    upsert(toUpdate) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            if (toUpdate == null) {
                return;
            }
            yield this.encryptedCollectionDataState.update((collections) => {
                if (collections == null) {
                    collections = {};
                }
                if (Array.isArray(toUpdate)) {
                    toUpdate.forEach((c) => {
                        collections[c.id] = c;
                    });
                }
                else {
                    collections[toUpdate.id] = toUpdate;
                }
                return collections;
            });
        });
    }
    replace(collections, userId) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider
                .getUser(userId, bw_ENCRYPTED_COLLECTION_DATA_KEY)
                .update(() => collections);
        });
    }
    clear(userId) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                yield this.encryptedCollectionDataState.update(() => null);
                yield this.decryptedCollectionDataState.forceValue(null);
            }
            else {
                yield this.stateProvider.getUser(userId, bw_ENCRYPTED_COLLECTION_DATA_KEY).update(() => null);
            }
        });
    }
    delete(id) {
        return bw_default_collection_service_awaiter(this, void 0, void 0, function* () {
            yield this.encryptedCollectionDataState.update((collections) => {
                if (collections == null) {
                    collections = {};
                }
                if (typeof id === "string") {
                    delete collections[id];
                }
                else {
                    id.forEach((i) => {
                        delete collections[i];
                    });
                }
                return collections;
            });
        });
    }
}

;// ../../libs/admin-console/src/common/collections/services/index.ts



;// ../../libs/admin-console/src/common/collections/index.ts




;// ../../libs/admin-console/src/common/index.ts



;// ../../libs/common/src/auth/models/request/update-temp-password.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_UpdateTempPasswordRequest extends bw_OrganizationUserResetPasswordRequest {
}

;// external "fs"
const bw_external_fs_namespaceObject = require("fs");
;// external "readline"
const bw_external_readline_namespaceObject = require("readline");
;// ../../libs/node/src/node-utils.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_NodeUtils {
    static mkdirpSync(targetDir, mode = "700", relative = false, relativeDir = null) {
        const initialDir = bw_external_path_namespaceObject.isAbsolute(targetDir) ? bw_external_path_namespaceObject.sep : "";
        const baseDir = relative ? (relativeDir != null ? relativeDir : __dirname) : ".";
        targetDir.split(bw_external_path_namespaceObject.sep).reduce((parentDir, childDir) => {
            const dir = bw_external_path_namespaceObject.resolve(baseDir, parentDir, childDir);
            if (!bw_external_fs_namespaceObject.existsSync(dir)) {
                bw_external_fs_namespaceObject.mkdirSync(dir, mode);
            }
            return dir;
        }, initialDir);
    }
    static readFirstLine(fileName) {
        return new Promise((resolve, reject) => {
            const readStream = bw_external_fs_namespaceObject.createReadStream(fileName, { encoding: "utf8" });
            const readInterface = bw_external_readline_namespaceObject.createInterface(readStream);
            readInterface
                .on("line", (line) => {
                readStream.close();
                resolve(line);
            })
                .on("error", (err) => reject(err));
        });
    }
    // https://stackoverflow.com/a/31394257
    static bufferToArrayBuffer(buf) {
        return buf.buffer.slice(buf.byteOffset, buf.byteOffset + buf.byteLength);
    }
}

;// ./src/auth/commands/login.command.ts
var bw_login_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
















class bw_LoginCommand {
    constructor(loginStrategyService, authService, apiService, masterPasswordApiService, cryptoFunctionService, environmentService, passwordGenerationService, passwordStrengthService, platformUtilsService, accountService, keyService, policyService, twoFactorService, syncService, keyConnectorService, policyApiService, orgService, logoutCallback, kdfConfigService, ssoUrlService) {
        this.loginStrategyService = loginStrategyService;
        this.authService = authService;
        this.apiService = apiService;
        this.masterPasswordApiService = masterPasswordApiService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.environmentService = environmentService;
        this.passwordGenerationService = passwordGenerationService;
        this.passwordStrengthService = passwordStrengthService;
        this.platformUtilsService = platformUtilsService;
        this.accountService = accountService;
        this.keyService = keyService;
        this.policyService = policyService;
        this.twoFactorService = twoFactorService;
        this.syncService = syncService;
        this.keyConnectorService = keyConnectorService;
        this.policyApiService = policyApiService;
        this.orgService = orgService;
        this.logoutCallback = logoutCallback;
        this.kdfConfigService = kdfConfigService;
        this.ssoUrlService = ssoUrlService;
        this.ssoRedirectUri = null;
    }
    run(email, password, options) {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            var _a;
            this.options = options;
            this.email = email;
            this.canInteract = process.env.BW_NOINTERACTION !== "true";
            let ssoCodeVerifier = null;
            let ssoCode = null;
            let orgIdentifier = null;
            let clientId = null;
            let clientSecret = null;
            let selectedProvider = null;
            if (options.apikey != null) {
                const apiIdentifiers = yield this.apiIdentifiers();
                clientId = apiIdentifiers.clientId;
                clientSecret = apiIdentifiers.clientSecret;
                if (clientId == null || clientId.trim() === "") {
                    return bw_Response.badRequest("client_id is required.");
                }
                if (clientSecret == null || clientSecret === "") {
                    return bw_Response.badRequest("client_secret is required.");
                }
            }
            else if (options.sso != null && this.canInteract) {
                const passwordOptions = {
                    type: "password",
                    length: 64,
                    uppercase: true,
                    lowercase: true,
                    numbers: true,
                    special: false,
                };
                const state = yield this.passwordGenerationService.generatePassword(passwordOptions);
                ssoCodeVerifier = yield this.passwordGenerationService.generatePassword(passwordOptions);
                const codeVerifierHash = yield this.cryptoFunctionService.hash(ssoCodeVerifier, "sha256");
                const codeChallenge = bw_utils_Utils.fromBufferToUrlB64(codeVerifierHash);
                try {
                    const ssoParams = yield this.openSsoPrompt(codeChallenge, state);
                    ssoCode = ssoParams.ssoCode;
                    orgIdentifier = ssoParams.orgIdentifier;
                }
                catch (_b) {
                    return bw_Response.badRequest("Something went wrong. Try again.");
                }
            }
            else {
                if ((email == null || email === "") && this.canInteract) {
                    const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                        output: process.stderr,
                    })({
                        type: "input",
                        name: "email",
                        message: "Email address:",
                    });
                    email = answer.email;
                }
                if (email == null || email.trim() === "") {
                    return bw_Response.badRequest("Email address is required.");
                }
                if (email.indexOf("@") === -1) {
                    return bw_Response.badRequest("Email address is invalid.");
                }
                this.email = email;
                if (password == null || password === "") {
                    if (options.passwordfile) {
                        password = yield bw_NodeUtils.readFirstLine(options.passwordfile);
                    }
                    else if (options.passwordenv && process.env[options.passwordenv]) {
                        password = process.env[options.passwordenv];
                    }
                    else if (this.canInteract) {
                        const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                            output: process.stderr,
                        })({
                            type: "password",
                            name: "password",
                            message: "Master password:",
                        });
                        password = answer.password;
                    }
                }
                if (password == null || password === "") {
                    return bw_Response.badRequest("Master password is required.");
                }
            }
            let twoFactorToken = options.code;
            let twoFactorMethod = null;
            try {
                if (options.method != null) {
                    twoFactorMethod = parseInt(options.method, null);
                }
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                return bw_Response.error("Invalid two-step login method.");
            }
            const twoFactor = twoFactorToken == null
                ? null
                : new bw_TokenTwoFactorRequest(twoFactorMethod, twoFactorToken, false);
            try {
                yield this.validatedParams();
                let response = null;
                if (clientId != null && clientSecret != null) {
                    if (!clientId.startsWith("user")) {
                        return bw_Response.error("Invalid API Key; Organization API Key currently not supported");
                    }
                    try {
                        response = yield this.loginStrategyService.logIn(new bw_UserApiLoginCredentials(clientId, clientSecret));
                    }
                    catch (e) {
                        // handle API key login failures
                        // Handle invalid client error as server doesn't return a useful message
                        if (((_a = e === null || e === void 0 ? void 0 : e.response) === null || _a === void 0 ? void 0 : _a.error) &&
                            typeof e.response.error === "string" &&
                            e.response.error === "invalid_client") {
                            return bw_Response.badRequest("client_id or client_secret is incorrect. Try again.");
                        }
                        // Pass error up to be handled by the outer catch block below
                        throw e;
                    }
                }
                else if (ssoCode != null && ssoCodeVerifier != null) {
                    response = yield this.loginStrategyService.logIn(new bw_SsoLoginCredentials(ssoCode, ssoCodeVerifier, this.ssoRedirectUri, orgIdentifier, undefined, // email to look up 2FA token not required as CLI can't remember 2FA token
                    twoFactor));
                }
                else {
                    response = yield this.loginStrategyService.logIn(new bw_PasswordLoginCredentials(email, password, null, twoFactor));
                }
                if (response.requiresEncryptionKeyMigration) {
                    return bw_Response.error("Encryption key migration required. Please login through the web vault to update your encryption key.");
                }
                if (response.captchaSiteKey) {
                    const credentials = new bw_PasswordLoginCredentials(email, password);
                    const handledResponse = yield this.handleCaptchaRequired(twoFactor, credentials);
                    // Error Response
                    if (handledResponse instanceof bw_Response) {
                        return handledResponse;
                    }
                    else {
                        response = handledResponse;
                    }
                }
                if (response.requiresTwoFactor) {
                    const twoFactorProviders = yield this.twoFactorService.getSupportedProviders(null);
                    if (twoFactorProviders.length === 0) {
                        return bw_Response.badRequest("No providers available for this client.");
                    }
                    if (twoFactorMethod != null) {
                        try {
                            selectedProvider = twoFactorProviders.filter((p) => p.type === twoFactorMethod)[0];
                            // FIXME: Remove when updating file. Eslint update
                            // eslint-disable-next-line @typescript-eslint/no-unused-vars
                        }
                        catch (e) {
                            return bw_Response.error("Invalid two-step login method.");
                        }
                    }
                    if (selectedProvider == null) {
                        if (twoFactorProviders.length === 1) {
                            selectedProvider = twoFactorProviders[0];
                        }
                        else if (this.canInteract) {
                            const twoFactorOptions = twoFactorProviders.map((p) => p.name);
                            twoFactorOptions.push(new bw_external_inquirer_namespaceObject.Separator());
                            twoFactorOptions.push("Cancel");
                            const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                                output: process.stderr,
                            })({
                                type: "list",
                                name: "method",
                                message: "Two-step login method:",
                                choices: twoFactorOptions,
                            });
                            const i = twoFactorOptions.indexOf(answer.method);
                            if (i === twoFactorOptions.length - 1) {
                                return bw_Response.error("Login failed.");
                            }
                            selectedProvider = twoFactorProviders[i];
                        }
                        if (selectedProvider == null) {
                            return bw_Response.error("Login failed. No provider selected.");
                        }
                    }
                    if (twoFactorToken == null &&
                        Object.keys(response.twoFactorProviders).length > 1 &&
                        selectedProvider.type === bw_TwoFactorProviderType.Email) {
                        const emailReq = new bw_TwoFactorEmailRequest();
                        emailReq.email = yield this.loginStrategyService.getEmail();
                        emailReq.masterPasswordHash = yield this.loginStrategyService.getMasterPasswordHash();
                        yield this.apiService.postTwoFactorEmail(emailReq);
                    }
                    if (twoFactorToken == null) {
                        if (this.canInteract) {
                            const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                                output: process.stderr,
                            })({
                                type: "input",
                                name: "token",
                                message: "Two-step login code:",
                            });
                            twoFactorToken = answer.token;
                        }
                        if (twoFactorToken == null || twoFactorToken === "") {
                            return bw_Response.badRequest("Code is required.");
                        }
                    }
                    response = yield this.loginStrategyService.logInTwoFactor(new bw_TokenTwoFactorRequest(selectedProvider.type, twoFactorToken), null);
                }
                // Opting for not checking feature flag since the server will not respond with
                // requiresDeviceVerification if the feature flag is not enabled.
                if (response.requiresDeviceVerification) {
                    let newDeviceToken = null;
                    if (this.canInteract) {
                        const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                            output: process.stderr,
                        })({
                            type: "input",
                            name: "token",
                            message: "New device verification required. Enter OTP sent to login email:",
                        });
                        newDeviceToken = answer.token;
                    }
                    if (newDeviceToken == null || newDeviceToken === "") {
                        return bw_Response.badRequest("Code is required.");
                    }
                    response = yield this.loginStrategyService.logInNewDeviceVerification(newDeviceToken);
                }
                if (response.captchaSiteKey) {
                    const twoFactorRequest = new bw_TokenTwoFactorRequest(selectedProvider.type, twoFactorToken);
                    const handledResponse = yield this.handleCaptchaRequired(twoFactorRequest);
                    // Error Response
                    if (handledResponse instanceof bw_Response) {
                        return handledResponse;
                    }
                    else {
                        response = handledResponse;
                    }
                }
                if (response.requiresTwoFactor) {
                    return bw_Response.error("Login failed.");
                }
                if (response.resetMasterPassword) {
                    return bw_Response.error("In order to log in with SSO from the CLI, you must first log in" +
                        " through the web vault to set your master password.");
                }
                // Run full sync before handling success response or password reset flows (to get Master Password Policies)
                yield this.syncService.fullSync(true);
                // Handle updating passwords if NOT using an API Key for authentication
                if (response.forcePasswordReset != bw_ForceSetPasswordReason.None &&
                    clientId == null &&
                    clientSecret == null) {
                    if (response.forcePasswordReset === bw_ForceSetPasswordReason.AdminForcePasswordReset) {
                        return yield this.updateTempPassword();
                    }
                    else if (response.forcePasswordReset === bw_ForceSetPasswordReason.WeakMasterPassword) {
                        return yield this.updateWeakPassword(password);
                    }
                }
                return yield this.handleSuccessResponse(response);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    validatedParams() {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            const key = yield this.cryptoFunctionService.randomBytes(64);
            process.env.BW_SESSION = bw_utils_Utils.fromBufferToB64(key);
        });
    }
    handleSuccessResponse(response) {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            const usesKeyConnector = yield this.keyConnectorService.getUsesKeyConnector(response.userId);
            if ((this.options.sso != null || this.options.apikey != null) &&
                this.canInteract &&
                !usesKeyConnector) {
                const res = new bw_MessageResponse("You are logged in!", "\n" + "To unlock your vault, use the `unlock` command. ex:\n" + "$ bw unlock");
                return bw_Response.success(res);
            }
            const res = new bw_MessageResponse("You are logged in!", "\n" +
                "To unlock your vault, set your session key to the `BW_SESSION` environment variable. ex:\n" +
                '$ export BW_SESSION="' +
                process.env.BW_SESSION +
                '"\n' +
                '> $env:BW_SESSION="' +
                process.env.BW_SESSION +
                '"\n\n' +
                "You can also pass the session key to any command with the `--session` option. ex:\n" +
                "$ bw list items --session " +
                process.env.BW_SESSION);
            res.raw = process.env.BW_SESSION;
            return bw_Response.success(res);
        });
    }
    handleUpdatePasswordSuccessResponse() {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            yield this.logoutCallback();
            this.authService.logOut(() => {
                /* Do nothing */
            });
            const res = new bw_MessageResponse("Your master password has been updated!", "\n" + "You have been logged out and must log in again to access the vault.");
            return bw_Response.success(res);
        });
    }
    updateWeakPassword(currentPassword) {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            // If no interaction available, alert user to use web vault
            if (!this.canInteract) {
                yield this.logoutCallback();
                this.authService.logOut(() => {
                    /* Do nothing */
                });
                return bw_Response.error(new bw_MessageResponse("Your master password does not meet one or more of your organization policies. In order to access the vault, you must update your master password now via the web vault. You have been logged out.", null));
            }
            try {
                const { newPasswordHash, newUserKey, hint } = yield this.collectNewMasterPasswordDetails("Your master password does not meet one or more of your organization policies. In order to access the vault, you must update your master password now.");
                const request = new bw_PasswordRequest();
                request.masterPasswordHash = yield this.keyService.hashMasterKey(currentPassword, null);
                request.masterPasswordHint = hint;
                request.newMasterPasswordHash = newPasswordHash;
                request.key = newUserKey[1].encryptedString;
                yield this.masterPasswordApiService.postPassword(request);
                return yield this.handleUpdatePasswordSuccessResponse();
            }
            catch (e) {
                yield this.logoutCallback();
                this.authService.logOut(() => {
                    /* Do nothing */
                });
                return bw_Response.error(e);
            }
        });
    }
    updateTempPassword() {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            // If no interaction available, alert user to use web vault
            if (!this.canInteract) {
                yield this.logoutCallback();
                this.authService.logOut(() => {
                    /* Do nothing */
                });
                return bw_Response.error(new bw_MessageResponse("An organization administrator recently changed your master password. In order to access the vault, you must update your master password now via the web vault. You have been logged out.", null));
            }
            try {
                const { newPasswordHash, newUserKey, hint } = yield this.collectNewMasterPasswordDetails("An organization administrator recently changed your master password. In order to access the vault, you must update your master password now.");
                const request = new bw_UpdateTempPasswordRequest();
                request.key = newUserKey[1].encryptedString;
                request.newMasterPasswordHash = newPasswordHash;
                request.masterPasswordHint = hint;
                yield this.masterPasswordApiService.putUpdateTempPassword(request);
                return yield this.handleUpdatePasswordSuccessResponse();
            }
            catch (e) {
                yield this.logoutCallback();
                this.authService.logOut(() => {
                    /* Do nothing */
                });
                return bw_Response.error(e);
            }
        });
    }
    /**
     * Collect new master password and hint from the CLI. The collected password
     * is validated against any applicable master password policies, a new master
     * key is generated, and we use it to re-encrypt the user key
     * @param prompt - Message that is displayed during the initial prompt
     * @param error
     */
    collectNewMasterPasswordDetails(prompt, error) {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            if (this.email == null || this.email === "undefined") {
                this.email = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.email)));
            }
            // Get New Master Password
            const baseMessage = `${prompt}\n` + "Master password: ";
            const firstMessage = error != null ? error + baseMessage : baseMessage;
            const mp = yield bw_external_inquirer_namespaceObject.createPromptModule({ output: process.stderr })({
                type: "password",
                name: "password",
                message: firstMessage,
            });
            const masterPassword = mp.password;
            // Master Password Validation
            if (masterPassword == null || masterPassword === "") {
                return this.collectNewMasterPasswordDetails(prompt, "Master password is required.\n");
            }
            if (masterPassword.length < bw_utils_Utils.minimumPasswordLength) {
                return this.collectNewMasterPasswordDetails(prompt, `Master password must be at least ${bw_utils_Utils.minimumPasswordLength} characters long.\n`);
            }
            // Strength & Policy Validation
            const strengthResult = this.passwordStrengthService.getPasswordStrength(masterPassword, this.email);
            const enforcedPolicyOptions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.policyService.masterPasswordPolicyOptions$());
            // Verify master password meets policy requirements
            if (enforcedPolicyOptions != null &&
                !this.policyService.evaluateMasterPassword(strengthResult.score, masterPassword, enforcedPolicyOptions)) {
                return this.collectNewMasterPasswordDetails(prompt, "Your new master password does not meet the policy requirements.\n");
            }
            // Get New Master Password Re-type
            const reTypeMessage = "Re-type New Master password (Strength: " + strengthResult.score + ")";
            const retype = yield bw_external_inquirer_namespaceObject.createPromptModule({ output: process.stderr })({
                type: "password",
                name: "password",
                message: reTypeMessage,
            });
            const masterPasswordRetype = retype.password;
            // Re-type Validation
            if (masterPassword !== masterPasswordRetype) {
                return this.collectNewMasterPasswordDetails(prompt, "Master password confirmation does not match.\n");
            }
            // Get Hint (optional)
            const hint = yield bw_external_inquirer_namespaceObject.createPromptModule({ output: process.stderr })({
                type: "input",
                name: "input",
                message: "Master Password Hint (optional):",
            });
            const masterPasswordHint = hint.input;
            const kdfConfig = yield this.kdfConfigService.getKdfConfig();
            // Create new key and hash new password
            const newMasterKey = yield this.keyService.makeMasterKey(masterPassword, this.email.trim().toLowerCase(), kdfConfig);
            const newPasswordHash = yield this.keyService.hashMasterKey(masterPassword, newMasterKey);
            // Grab user key
            const userKey = yield this.keyService.getUserKey();
            if (!userKey) {
                throw new Error("User key not found.");
            }
            // Re-encrypt user key with new master key
            const newUserKey = yield this.keyService.encryptUserKeyWithMasterKey(newMasterKey, userKey);
            return { newPasswordHash, newUserKey: newUserKey, hint: masterPasswordHint };
        });
    }
    handleCaptchaRequired(twoFactorRequest_1) {
        return bw_login_command_awaiter(this, arguments, void 0, function* (twoFactorRequest, credentials = null) {
            const badCaptcha = bw_Response.badRequest("Your authentication request has been flagged and will require user interaction to proceed.\n" +
                "Please use your API key to validate this request and ensure BW_CLIENTSECRET is correct, if set.\n" +
                "(https://bitwarden.com/help/cli-auth-challenges)");
            try {
                const captchaClientSecret = yield this.apiClientSecret(true);
                if (bw_utils_Utils.isNullOrWhitespace(captchaClientSecret)) {
                    return badCaptcha;
                }
                let authResultResponse = null;
                if (credentials != null) {
                    credentials.captchaToken = captchaClientSecret;
                    credentials.twoFactor = twoFactorRequest;
                    authResultResponse = yield this.loginStrategyService.logIn(credentials);
                }
                else {
                    authResultResponse = yield this.loginStrategyService.logInTwoFactor(twoFactorRequest, captchaClientSecret);
                }
                return authResultResponse;
            }
            catch (e) {
                if (e instanceof bw_ErrorResponse ||
                    (e.constructor.name === bw_ErrorResponse.name &&
                        e.message.includes("Captcha is invalid"))) {
                    return badCaptcha;
                }
                else {
                    return bw_Response.error(e);
                }
            }
        });
    }
    apiClientId() {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            let clientId = null;
            const storedClientId = process.env.BW_CLIENTID;
            if (storedClientId == null) {
                if (this.canInteract) {
                    const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                        output: process.stderr,
                    })({
                        type: "input",
                        name: "clientId",
                        message: "client_id:",
                    });
                    clientId = answer.clientId;
                }
                else {
                    clientId = null;
                }
            }
            else {
                clientId = storedClientId;
            }
            return clientId;
        });
    }
    apiClientSecret() {
        return bw_login_command_awaiter(this, arguments, void 0, function* (isAdditionalAuthentication = false) {
            const additionalAuthenticationMessage = "Additional authentication required.\nAPI key ";
            let clientSecret = null;
            const storedClientSecret = this.clientSecret || process.env.BW_CLIENTSECRET;
            if (storedClientSecret == null) {
                if (this.canInteract) {
                    const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                        output: process.stderr,
                    })({
                        type: "input",
                        name: "clientSecret",
                        message: (isAdditionalAuthentication ? additionalAuthenticationMessage : "") + "client_secret:",
                    });
                    clientSecret = answer.clientSecret;
                }
                else {
                    clientSecret = null;
                }
            }
            else {
                clientSecret = storedClientSecret;
            }
            return clientSecret;
        });
    }
    apiIdentifiers() {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            return {
                clientId: yield this.apiClientId(),
                clientSecret: yield this.apiClientSecret(),
            };
        });
    }
    openSsoPrompt(codeChallenge, state) {
        return bw_login_command_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            return new Promise((resolve, reject) => {
                const callbackServer = bw_external_http_namespaceObject.createServer((req, res) => {
                    const urlString = "http://localhost" + req.url;
                    const url = new URL(urlString);
                    const code = url.searchParams.get("code");
                    const receivedState = url.searchParams.get("state");
                    const orgIdentifier = this.getOrgIdentifierFromState(receivedState);
                    res.setHeader("Content-Type", "text/html");
                    if (code != null && receivedState != null && this.checkState(receivedState, state)) {
                        res.writeHead(200);
                        res.end("<html><head><title>Success | Bitwarden CLI</title></head><body>" +
                            "<h1>Successfully authenticated with the Bitwarden CLI</h1>" +
                            "<p>You may now close this tab and return to the terminal.</p>" +
                            "</body></html>");
                        callbackServer.close(() => resolve({
                            ssoCode: code,
                            orgIdentifier: orgIdentifier,
                        }));
                    }
                    else {
                        res.writeHead(400);
                        res.end("<html><head><title>Failed | Bitwarden CLI</title></head><body>" +
                            "<h1>Something went wrong logging into the Bitwarden CLI</h1>" +
                            "<p>You may now close this tab and return to the terminal.</p>" +
                            "</body></html>");
                        callbackServer.close(() => reject());
                    }
                });
                let foundPort = false;
                const webUrl = env.getWebVaultUrl();
                for (let port = 8065; port <= 8070; port++) {
                    try {
                        this.ssoRedirectUri = "http://localhost:" + port;
                        callbackServer.listen(port, () => {
                            const webAppSsoUrl = this.ssoUrlService.buildSsoUrl(webUrl, bw_ClientType.Cli, this.ssoRedirectUri, state, codeChallenge);
                            this.platformUtilsService.launchUri(webAppSsoUrl);
                        });
                        foundPort = true;
                        break;
                    }
                    catch (_a) {
                        // Ignore error since we run the same command up to 5 times.
                    }
                }
                if (!foundPort) {
                    reject();
                }
            });
        });
    }
    getOrgIdentifierFromState(state) {
        if (state === null || state === undefined) {
            return null;
        }
        const stateSplit = state.split("_identifier=");
        return stateSplit.length > 1 ? stateSplit[1] : null;
    }
    checkState(state, checkState) {
        if (state === null || state === undefined) {
            return false;
        }
        if (checkState === null || checkState === undefined) {
            return false;
        }
        const stateSplit = state.split("_identifier=");
        const checkStateSplit = checkState.split("_identifier=");
        return stateSplit[0] === checkStateSplit[0];
    }
}

;// ./src/auth/commands/logout.command.ts
var bw_logout_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_LogoutCommand {
    constructor(authService, i18nService, logoutCallback) {
        this.authService = authService;
        this.i18nService = i18nService;
        this.logoutCallback = logoutCallback;
    }
    run() {
        return bw_logout_command_awaiter(this, void 0, void 0, function* () {
            yield this.logoutCallback();
            this.authService.logOut(() => {
                /* Do nothing */
            });
            const res = new bw_MessageResponse("You have logged out.", null);
            return bw_Response.success(res);
        });
    }
}

;// ../../libs/common/src/auth/enums/verification-type.ts
var bw_VerificationType;
(function (VerificationType) {
    VerificationType[VerificationType["MasterPassword"] = 0] = "MasterPassword";
    VerificationType[VerificationType["OTP"] = 1] = "OTP";
    VerificationType[VerificationType["PIN"] = 2] = "PIN";
    VerificationType[VerificationType["Biometrics"] = 3] = "Biometrics";
})(bw_VerificationType || (bw_VerificationType = {}));

;// ../../libs/common/src/platform/abstractions/environment.service.ts
/**
 * A subset of available regions, additional regions can be loaded through configuration.
 */
var bw_Region;
(function (Region) {
    Region["US"] = "US";
    Region["EU"] = "EU";
    Region["SelfHosted"] = "Self-hosted";
})(bw_Region || (bw_Region = {}));
/**
 * The environment service. Provides access to set the current environment urls and region.
 */
class bw_EnvironmentService {
}

;// ./src/commands/convert-to-key-connector.command.ts
var bw_convert_to_key_connector_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_ConvertToKeyConnectorCommand {
    constructor(userId, keyConnectorService, environmentService, syncService, organizationApiService, logout) {
        this.userId = userId;
        this.keyConnectorService = keyConnectorService;
        this.environmentService = environmentService;
        this.syncService = syncService;
        this.organizationApiService = organizationApiService;
        this.logout = logout;
    }
    run() {
        return bw_convert_to_key_connector_command_awaiter(this, void 0, void 0, function* () {
            // If no interaction available, alert user to use web vault
            const canInteract = process.env.BW_NOINTERACTION !== "true";
            if (!canInteract) {
                yield this.logout();
                return bw_Response.error(new bw_MessageResponse("An organization you are a member of is using Key Connector. " +
                    "In order to access the vault, you must opt-in to Key Connector now via the web vault. You have been logged out.", null));
            }
            const organization = yield this.keyConnectorService.getManagingOrganization();
            const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({ output: process.stderr })({
                type: "list",
                name: "convert",
                message: organization.name +
                    " is using a self-hosted key server. A master password is no longer required to log in for members of this organization. ",
                choices: [
                    {
                        name: "Remove master password and unlock",
                        value: "remove",
                    },
                    {
                        name: "Leave organization and unlock",
                        value: "leave",
                    },
                    {
                        name: "Log out",
                        value: "exit",
                    },
                ],
            });
            if (answer.convert === "remove") {
                try {
                    yield this.keyConnectorService.migrateUser();
                }
                catch (e) {
                    yield this.logout();
                    throw e;
                }
                yield this.keyConnectorService.removeConvertAccountRequired();
                yield this.keyConnectorService.setUsesKeyConnector(true, this.userId);
                // Update environment URL - required for api key login
                const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
                const urls = env.getUrls();
                urls.keyConnector = organization.keyConnectorUrl;
                yield this.environmentService.setEnvironment(bw_Region.SelfHosted, urls);
                return bw_Response.success();
            }
            else if (answer.convert === "leave") {
                yield this.organizationApiService.leave(organization.id);
                yield this.keyConnectorService.removeConvertAccountRequired();
                return bw_Response.success();
            }
            else {
                yield this.logout();
                return bw_Response.error("You have been logged out.");
            }
        });
    }
}

;// external "jszip"
const bw_external_jszip_namespaceObject = require("jszip");
;// ./src/utils.ts
var bw_utils_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore








class bw_CliUtils {
    static writeLn(s, finalLine = false, error = false) {
        const stream = error ? process.stderr : process.stdout;
        if (finalLine && (process.platform === "win32" || !stream.isTTY)) {
            stream.write(s);
        }
        else {
            stream.write(s + "\n");
        }
    }
    static readFile(input) {
        return new Promise((resolve, reject) => {
            let p = null;
            if (input != null && input !== "") {
                const osInput = bw_external_path_namespaceObject.join(input);
                if (osInput.indexOf(bw_external_path_namespaceObject.sep) === -1) {
                    p = bw_external_path_namespaceObject.join(process.cwd(), osInput);
                }
                else {
                    p = osInput;
                }
            }
            else {
                reject("You must specify a file path.");
            }
            bw_external_fs_namespaceObject.readFile(p, "utf8", (err, data) => {
                if (err != null) {
                    reject(err.message);
                }
                resolve(data);
            });
        });
    }
    static extractZipContent(input, filepath) {
        return new Promise((resolve, reject) => {
            let p = null;
            if (input != null && input !== "") {
                const osInput = bw_external_path_namespaceObject.join(input);
                if (osInput.indexOf(bw_external_path_namespaceObject.sep) === -1) {
                    p = bw_external_path_namespaceObject.join(process.cwd(), osInput);
                }
                else {
                    p = osInput;
                }
            }
            else {
                reject("You must specify a file path.");
            }
            bw_external_fs_namespaceObject.readFile(p, function (err, data) {
                if (err) {
                    reject(err);
                }
                bw_external_jszip_namespaceObject.loadAsync(data).then((zip) => {
                    resolve(zip.file(filepath).async("string"));
                }, (reason) => {
                    reject(reason);
                });
            });
        });
    }
    /**
     * Save the given data to a file and determine the target file if necessary.
     * If output is non-empty, it is used as target filename. Otherwise the target filename is
     * built from the current working directory and the given defaultFileName.
     *
     * @param data to be written to the file.
     * @param output file to write to or empty to choose automatically.
     * @param defaultFileName to use when no explicit output filename is given.
     * @return the chosen output file.
     */
    static saveFile(data, output, defaultFileName) {
        let p = null;
        let mkdir = false;
        if (output != null && output !== "") {
            const osOutput = bw_external_path_namespaceObject.join(output);
            if (osOutput.indexOf(bw_external_path_namespaceObject.sep) === -1) {
                p = bw_external_path_namespaceObject.join(process.cwd(), osOutput);
            }
            else {
                mkdir = true;
                if (osOutput.endsWith(bw_external_path_namespaceObject.sep)) {
                    p = bw_external_path_namespaceObject.join(osOutput, defaultFileName);
                }
                else {
                    p = osOutput;
                }
            }
        }
        else {
            p = bw_external_path_namespaceObject.join(process.cwd(), defaultFileName);
        }
        p = bw_external_path_namespaceObject.resolve(p);
        if (mkdir) {
            const dir = p.substring(0, p.lastIndexOf(bw_external_path_namespaceObject.sep));
            if (!bw_external_fs_namespaceObject.existsSync(dir)) {
                bw_NodeUtils.mkdirpSync(dir, "700");
            }
        }
        return new Promise((resolve, reject) => {
            bw_external_fs_namespaceObject.writeFile(p, data, { encoding: "utf8", mode: 0o600 }, (err) => {
                if (err != null) {
                    reject("Cannot save file to " + p);
                }
                resolve(p);
            });
        });
    }
    /**
     * Process the given data and write it to a file if possible. If the user requested RAW output and
     * no output name is given, the file is directly written to stdout. The resulting Response contains
     * an otherwise empty message then to prevent writing other information to stdout.
     *
     * If an output is given or no RAW output is requested, the rules from [saveFile] apply.
     *
     * @param data to be written to the file or stdout.
     * @param output file to write to or empty to choose automatically.
     * @param defaultFileName to use when no explicit output filename is given.
     * @return an empty [Response] if written to stdout or a [Response] with the chosen output file otherwise.
     */
    static saveResultToFile(data, output, defaultFileName) {
        return bw_utils_awaiter(this, void 0, void 0, function* () {
            if ((output == null || output === "") && process.env.BW_RAW === "true") {
                // No output is given and the user expects raw output. Since the command result is about content,
                // we directly return the command result to stdout (and suppress further messages).
                process.stdout.write(data);
                return bw_Response.success();
            }
            const filePath = yield this.saveFile(data, output, defaultFileName);
            const res = new bw_MessageResponse("Saved " + filePath, null);
            res.raw = filePath;
            return bw_Response.success(res);
        });
    }
    static readStdin() {
        return new Promise((resolve, reject) => {
            let input = "";
            if (process.stdin.isTTY) {
                resolve(input);
                return;
            }
            process.stdin.setEncoding("utf8");
            process.stdin.on("readable", () => {
                // eslint-disable-next-line
                while (true) {
                    const chunk = process.stdin.read();
                    if (chunk == null) {
                        break;
                    }
                    input += chunk;
                }
            });
            process.stdin.on("end", () => {
                resolve(input);
            });
        });
    }
    static searchFolders(folders, search) {
        search = search.toLowerCase();
        return folders.filter((f) => {
            if (f.name != null && f.name.toLowerCase().indexOf(search) > -1) {
                return true;
            }
            return false;
        });
    }
    static searchCollections(collections, search) {
        search = search.toLowerCase();
        return collections.filter((c) => {
            if (c.name != null && c.name.toLowerCase().indexOf(search) > -1) {
                return true;
            }
            return false;
        });
    }
    static searchOrganizations(organizations, search) {
        search = search.toLowerCase();
        return organizations.filter((o) => {
            if (o.name != null && o.name.toLowerCase().indexOf(search) > -1) {
                return true;
            }
            return false;
        });
    }
    /**
     * Gets a password from all available sources. In order of priority these are:
     *   * passwordfile
     *   * passwordenv
     *   * user interaction
     *
     * Returns password string if successful, Response if not.
     */
    static getPassword(password, options, logService) {
        return bw_utils_awaiter(this, void 0, void 0, function* () {
            if (bw_utils_Utils.isNullOrEmpty(password)) {
                if (options === null || options === void 0 ? void 0 : options.passwordFile) {
                    password = yield bw_NodeUtils.readFirstLine(options.passwordFile);
                }
                else if (options === null || options === void 0 ? void 0 : options.passwordEnv) {
                    if (process.env[options.passwordEnv]) {
                        password = process.env[options.passwordEnv];
                    }
                    else if (logService) {
                        logService.warning(`Warning: Provided passwordenv ${options.passwordEnv} is not set`);
                    }
                }
            }
            if (bw_utils_Utils.isNullOrEmpty(password)) {
                if (process.env.BW_NOINTERACTION !== "true") {
                    const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                        output: process.stderr,
                    })({
                        type: "password",
                        name: "password",
                        message: "Master password:",
                    });
                    password = answer.password;
                }
                else {
                    return bw_Response.badRequest("Master password is required. Try again in interactive mode or provide a password file or environment variable.");
                }
            }
            return password;
        });
    }
    static convertBooleanOption(optionValue) {
        return optionValue || optionValue === "" ? true : false;
    }
    static convertNumberOption(optionValue, defaultValue) {
        try {
            if (optionValue != null) {
                const numVal = parseInt(optionValue);
                return !Number.isNaN(numVal) ? numVal : defaultValue;
            }
            return defaultValue;
        }
        catch (_a) {
            return defaultValue;
        }
    }
    static convertStringOption(optionValue, defaultValue) {
        return optionValue != null ? String(optionValue) : defaultValue;
    }
}

;// ./src/auth/commands/unlock.command.ts
var bw_unlock_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







class bw_UnlockCommand {
    constructor(accountService, masterPasswordService, keyService, userVerificationService, cryptoFunctionService, logService, keyConnectorService, environmentService, syncService, organizationApiService, logout) {
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.keyService = keyService;
        this.userVerificationService = userVerificationService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.logService = logService;
        this.keyConnectorService = keyConnectorService;
        this.environmentService = environmentService;
        this.syncService = syncService;
        this.organizationApiService = organizationApiService;
        this.logout = logout;
    }
    run(password, cmdOptions) {
        return bw_unlock_command_awaiter(this, void 0, void 0, function* () {
            const normalizedOptions = new bw_Options(cmdOptions);
            const passwordResult = yield bw_CliUtils.getPassword(password, normalizedOptions, this.logService);
            if (passwordResult instanceof bw_Response) {
                return passwordResult;
            }
            else {
                password = passwordResult;
            }
            yield this.setNewSessionKey();
            const [userId, email] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => [a === null || a === void 0 ? void 0 : a.id, a === null || a === void 0 ? void 0 : a.email])));
            const verification = {
                type: bw_VerificationType.MasterPassword,
                secret: password,
            };
            let masterKey;
            try {
                const response = yield this.userVerificationService.verifyUserByMasterPassword(verification, userId, email);
                masterKey = response.masterKey;
            }
            catch (e) {
                // verification failure throws
                return bw_Response.error(e.message);
            }
            const userKey = yield this.masterPasswordService.decryptUserKeyWithMasterKey(masterKey, userId);
            yield this.keyService.setUserKey(userKey, userId);
            if (yield this.keyConnectorService.getConvertAccountRequired()) {
                const convertToKeyConnectorCommand = new bw_ConvertToKeyConnectorCommand(userId, this.keyConnectorService, this.environmentService, this.syncService, this.organizationApiService, this.logout);
                const convertResponse = yield convertToKeyConnectorCommand.run();
                if (!convertResponse.success) {
                    return convertResponse;
                }
            }
            return this.successResponse();
        });
    }
    setNewSessionKey() {
        return bw_unlock_command_awaiter(this, void 0, void 0, function* () {
            const key = yield this.cryptoFunctionService.randomBytes(64);
            process.env.BW_SESSION = bw_utils_Utils.fromBufferToB64(key);
        });
    }
    successResponse() {
        return bw_unlock_command_awaiter(this, void 0, void 0, function* () {
            const res = new bw_MessageResponse("Your vault is now unlocked!", "\n" +
                "To unlock your vault, set your session key to the `BW_SESSION` environment variable. ex:\n" +
                '$ export BW_SESSION="' +
                process.env.BW_SESSION +
                '"\n' +
                '> $env:BW_SESSION="' +
                process.env.BW_SESSION +
                '"\n\n' +
                "You can also pass the session key to any command with the `--session` option. ex:\n" +
                "$ bw list items --session " +
                process.env.BW_SESSION);
            res.raw = process.env.BW_SESSION;
            return bw_Response.success(res);
        });
    }
}
class bw_Options {
    constructor(passedOptions) {
        this.passwordEnv = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.passwordenv) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.passwordEnv);
        this.passwordFile = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.passwordfile) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.passwordFile);
    }
}

;// ./src/base-program.ts
var bw_base_program_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






const bw_writeLn = bw_CliUtils.writeLn;
class bw_BaseProgram {
    constructor(serviceContainer) {
        this.serviceContainer = serviceContainer;
    }
    processResponse(response, exitImmediately = false) {
        if (!response.success) {
            if (process.env.BW_QUIET !== "true") {
                if (process.env.BW_RESPONSE === "true") {
                    bw_writeLn(this.getJson(response), true, false);
                }
                else {
                    bw_writeLn(bw_external_chalk_namespaceObject.redBright(response.message), true, true);
                }
            }
            const exitCode = process.env.BW_CLEANEXIT ? 0 : 1;
            if (exitImmediately) {
                process.exit(exitCode);
            }
            else {
                process.exitCode = exitCode;
            }
            return;
        }
        if (process.env.BW_RESPONSE === "true") {
            bw_writeLn(this.getJson(response), true, false);
        }
        else if (response.data != null) {
            let out = null;
            if (response.data.object === "template") {
                out = this.getJson(response.data.template);
            }
            if (out == null) {
                if (response.data.object === "string") {
                    const data = response.data.data;
                    if (data != null) {
                        out = data;
                    }
                }
                else if (response.data.object === "list") {
                    out = this.getJson(response.data.data);
                }
                else if (response.data.object === "message") {
                    out = this.getMessage(response);
                }
                else {
                    out = this.getJson(response.data);
                }
            }
            if (out != null && process.env.BW_QUIET !== "true") {
                bw_writeLn(out, true, false);
            }
        }
        if (exitImmediately) {
            process.exit(0);
        }
        else {
            process.exitCode = 0;
        }
    }
    getJson(obj) {
        if (process.env.BW_PRETTY === "true") {
            return JSON.stringify(obj, null, "  ");
        }
        else {
            return JSON.stringify(obj);
        }
    }
    getMessage(response) {
        const message = response.data;
        if (process.env.BW_RAW === "true") {
            return message.raw;
        }
        let out = "";
        if (message.title != null) {
            if (message.noColor) {
                out = message.title;
            }
            else {
                out = bw_external_chalk_namespaceObject.greenBright(message.title);
            }
        }
        if (message.message != null) {
            if (message.title != null) {
                out += "\n";
            }
            out += message.message;
        }
        return out.trim() === "" ? null : out;
    }
    exitIfAuthed() {
        return bw_base_program_awaiter(this, void 0, void 0, function* () {
            const authed = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.serviceContainer.authService.activeAccountStatus$.pipe((0,bw_external_rxjs_namespaceObject.map)((status) => status > bw_authentication_status_AuthenticationStatus.LoggedOut)));
            if (authed) {
                const email = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.serviceContainer.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.email)));
                this.processResponse(bw_Response.error("You are already logged in as " + email + "."), true);
            }
        });
    }
    /**
     * Exist if no user is authenticated
     * @returns the userId of the active account
     */
    exitIfNotAuthed() {
        return bw_base_program_awaiter(this, void 0, void 0, function* () {
            var _a;
            const fail = () => this.processResponse(bw_Response.error("You are not logged in."), true);
            const userId = (_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.serviceContainer.accountService.activeAccount$))) === null || _a === void 0 ? void 0 : _a.id;
            if (!userId) {
                fail();
            }
            const authed = yield this.serviceContainer.stateService.getIsAuthenticated({ userId });
            if (!authed) {
                fail();
            }
            return userId;
        });
    }
    exitIfLocked() {
        return bw_base_program_awaiter(this, void 0, void 0, function* () {
            const userId = yield this.exitIfNotAuthed();
            // If the process.env does not have a BW_SESSION key, then we will never be able to retrieve
            // the auto user key from secure storage. This is because the auto user key is encrypted with
            // the session key.
            const hasUserKey = yield this.serviceContainer.userAutoUnlockKeyService.setUserKeyInMemoryIfAutoUserKeySet(userId);
            if (hasUserKey) {
                // User is unlocked
                return;
            }
            // User is locked
            yield this.handleLockedUser(userId);
        });
    }
    handleLockedUser(userId) {
        return bw_base_program_awaiter(this, void 0, void 0, function* () {
            if (process.env.BW_NOINTERACTION === "true") {
                this.processResponse(bw_Response.error("Vault is locked."), true);
                return;
            }
            // must unlock with interaction allowed
            if (yield this.serviceContainer.keyConnectorService.getUsesKeyConnector(userId)) {
                const response = bw_Response.error("Your vault is locked. You must unlock your vault using your session key.\n" +
                    "If you do not have your session key, you can get a new one by logging out and logging in again.");
                this.processResponse(response, true);
            }
            else {
                const command = new bw_UnlockCommand(this.serviceContainer.accountService, this.serviceContainer.masterPasswordService, this.serviceContainer.keyService, this.serviceContainer.userVerificationService, this.serviceContainer.cryptoFunctionService, this.serviceContainer.logService, this.serviceContainer.keyConnectorService, this.serviceContainer.environmentService, this.serviceContainer.syncService, this.serviceContainer.organizationApiService, this.serviceContainer.logout);
                const response = yield command.run(null, null);
                if (!response.success) {
                    this.processResponse(response, true);
                }
            }
        });
    }
    exitIfFeatureFlagDisabled(featureFlag) {
        return bw_base_program_awaiter(this, void 0, void 0, function* () {
            const enabled = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.serviceContainer.configService.getFeatureFlag$(featureFlag));
            if (!enabled) {
                this.processResponse(bw_Response.error("This command is temporarily unavailable."), true);
            }
        });
    }
}

;// ./src/commands/completion.command.ts
var bw_completion_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



const bw_validShells = ["zsh"];
class bw_CompletionCommand {
    run(options) {
        return bw_completion_command_awaiter(this, void 0, void 0, function* () {
            const shell = options.shell;
            if (!shell) {
                return bw_Response.badRequest("`shell` option was not provided.");
            }
            if (!bw_validShells.includes(shell)) {
                return bw_Response.badRequest("Unsupported shell.");
            }
            let content = "";
            if (shell === "zsh") {
                content = this.zshCompletion("bw", bw_external_commander_namespaceObject.program).render();
            }
            const res = new bw_MessageResponse(content, null);
            return bw_Response.success(res);
        });
    }
    zshCompletion(rootName, rootCommand) {
        return {
            render: () => {
                return [
                    `#compdef _${rootName} ${rootName}`,
                    "",
                    this.renderCommandBlock(rootName, rootCommand),
                ].join("\n");
            },
        };
    }
    renderCommandBlock(name, command) {
        const { commands = [], options = [] } = command;
        const hasOptions = options.length > 0;
        const hasCommands = commands.length > 0;
        const args = options
            .map(({ long, short, description }) => {
            const aliases = [short, long].filter(Boolean);
            const opts = aliases.join(",");
            const desc = `[${description.replace(`'`, `'"'"'`)}]`;
            return aliases.length > 1
                ? `'(${aliases.join(" ")})'{${opts}}'${desc}'`
                : `'${opts}${desc}'`;
        })
            .concat(`'(-h --help)'{-h,--help}'[output usage information]'`, hasCommands ? '"1: :->cmnds"' : null, '"*::arg:->args"')
            .filter(Boolean);
        const commandBlockFunctionParts = [];
        if (hasCommands) {
            commandBlockFunctionParts.push("local -a commands");
        }
        if (hasOptions) {
            commandBlockFunctionParts.push(`_arguments -C \\\n    ${args.join(` \\\n    `)}`);
        }
        if (hasCommands) {
            commandBlockFunctionParts.push(`case $state in
    cmnds)
      commands=(
        ${commands
                .map((command) => `"${command.name().split(" ")[0]}:${command.description()}"`)
                .join("\n        ")}
      )
      _describe "command" commands
      ;;\n  esac

  case "$words[1]" in
    ${commands
                .map((command) => {
                const commandName = command.name().split(" ")[0];
                return [`${commandName})`, `_${name}_${commandName}`, ";;"].join("\n      ");
            })
                .join("\n    ")}\n  esac`);
        }
        const commandBlocParts = [
            `function _${name} {\n  ${commandBlockFunctionParts.join("\n\n  ")}\n}`,
        ];
        if (hasCommands) {
            commandBlocParts.push(commands.map((c) => this.renderCommandBlock(`${name}_${c.name()}`, c)).join("\n\n"));
        }
        return commandBlocParts.join("\n\n");
    }
}

;// ./src/models/response/string.response.ts
class bw_StringResponse {
    constructor(data) {
        this.object = "string";
        this.data = data;
    }
}

;// ./src/commands/encode.command.ts
var bw_encode_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_EncodeCommand {
    run() {
        return bw_encode_command_awaiter(this, void 0, void 0, function* () {
            if (process.stdin.isTTY) {
                return bw_Response.badRequest("No stdin was piped in.");
            }
            const input = yield bw_CliUtils.readStdin();
            const b64 = Buffer.from(input, "utf8").toString("base64");
            const res = new bw_StringResponse(b64);
            return bw_Response.success(res);
        });
    }
}

;// ./src/models/response/template.response.ts
class bw_TemplateResponse {
    constructor(template) {
        this.object = "template";
        this.template = template;
    }
}

;// ./src/commands/status.command.ts
var bw_status_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_StatusCommand {
    constructor(envService, syncService, accountService, authService) {
        this.envService = envService;
        this.syncService = syncService;
        this.accountService = accountService;
        this.authService = authService;
    }
    run() {
        return bw_status_command_awaiter(this, void 0, void 0, function* () {
            try {
                const baseUrl = yield this.baseUrl();
                const status = yield this.status();
                const lastSync = yield this.syncService.getLastSync();
                const [userId, email] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => [a === null || a === void 0 ? void 0 : a.id, a === null || a === void 0 ? void 0 : a.email])));
                return bw_Response.success(new bw_TemplateResponse({
                    serverUrl: baseUrl,
                    lastSync: lastSync,
                    userEmail: email,
                    userId: userId,
                    status: status,
                }));
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    baseUrl() {
        return bw_status_command_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.envService.environment$);
            return env.getUrls().base;
        });
    }
    status() {
        return bw_status_command_awaiter(this, void 0, void 0, function* () {
            const authStatus = yield this.authService.getAuthStatus();
            if (authStatus === bw_authentication_status_AuthenticationStatus.Unlocked) {
                return "unlocked";
            }
            else if (authStatus === bw_authentication_status_AuthenticationStatus.Locked) {
                return "locked";
            }
            else {
                return "unauthenticated";
            }
        });
    }
}

;// ./src/commands/update.command.ts
var bw_update_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


const bw_CLIENTS_RELEASE_LIST_ENDPOINT = "https://api.github.com/repos/bitwarden/clients/releases";
const bw_DEFAULT_DOWNLOAD_URL = "https://github.com/bitwarden/clients/releases";
const bw_UPDATE_COMMAND = "npm install -g @bitwarden/cli";
class bw_UpdateCommand {
    constructor(platformUtilsService, apiService) {
        this.platformUtilsService = platformUtilsService;
        this.apiService = apiService;
        this.inPkg = false;
        this.inPkg = !!process.pkg;
    }
    run() {
        return bw_update_command_awaiter(this, void 0, void 0, function* () {
            const response = yield this.apiService.nativeFetch(new Request(bw_CLIENTS_RELEASE_LIST_ENDPOINT));
            if (response.status !== 200) {
                return bw_Response.error("Error contacting update API: " + response.status);
            }
            const responseJson = yield response.json();
            const cliRelease = responseJson.find((r) => r.tag_name.includes("cli"));
            if (cliRelease === undefined || cliRelease === null) {
                return bw_Response.error("Could not find latest CLI version.");
            }
            const currentVersion = yield this.platformUtilsService.getApplicationVersion();
            if (cliRelease.tag_name === "cli-v" + currentVersion) {
                const response = new bw_MessageResponse(null, null);
                response.title = "No update available.";
                response.noColor = true;
                return bw_Response.success(response);
            }
            const res = this.getFoundUpdateResponse(cliRelease);
            return bw_Response.success(res);
        });
    }
    getFoundUpdateResponse(release) {
        const downloadUrl = this.getDownloadUrl(release.assets);
        const response = new bw_MessageResponse(null, null);
        response.title = "A new version is available: " + release.tag_name;
        response.raw = downloadUrl;
        response.message = this.getMessage(release, downloadUrl);
        return response;
    }
    getMessage(release, downloadUrl) {
        let message = "";
        if (release.body != null && release.body !== "") {
            message = release.body + "\n\n";
        }
        message += "You can download this update at " + downloadUrl;
        if (this.inPkg) {
            message +=
                "\n\nIf you installed this CLI through a package manager " +
                    "you should probably update using its update command instead.";
        }
        else {
            message +=
                "\n\nIf you installed this CLI through NPM " +
                    "you should update using `" +
                    bw_UPDATE_COMMAND +
                    "`";
        }
        return message;
    }
    getDownloadUrl(assets) {
        if (assets == null) {
            return bw_DEFAULT_DOWNLOAD_URL;
        }
        let downloadUrl = bw_DEFAULT_DOWNLOAD_URL;
        for (const a of assets) {
            const download = a.browser_download_url;
            if (download == null) {
                continue;
            }
            if (download.indexOf(".zip") === -1) {
                continue;
            }
            if (process.platform === "win32" && download.indexOf("bw-windows") > -1) {
                downloadUrl = download;
                break;
            }
            else if (process.platform === "darwin" && download.indexOf("bw-macos") > -1) {
                downloadUrl = download;
                break;
            }
            else if (process.platform === "linux" && download.indexOf("bw-linux") > -1) {
                downloadUrl = download;
                break;
            }
        }
        return downloadUrl;
    }
}

;// ./src/platform/commands/config.command.ts
var bw_config_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_ConfigCommand {
    constructor(environmentService, accountService) {
        this.environmentService = environmentService;
        this.accountService = accountService;
    }
    run(setting, value, options) {
        return bw_config_command_awaiter(this, void 0, void 0, function* () {
            setting = setting.toLowerCase();
            switch (setting) {
                case "server":
                    return yield this.getOrSetServer(value, options);
                default:
                    return bw_Response.badRequest("Unknown setting.");
            }
        });
    }
    getOrSetServer(url, options) {
        return bw_config_command_awaiter(this, void 0, void 0, function* () {
            if ((url == null || url.trim() === "") &&
                !options.webVault &&
                !options.api &&
                !options.identity &&
                !options.icons &&
                !options.notifications &&
                !options.events) {
                const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
                const stringRes = new bw_StringResponse(env.hasBaseUrl() ? env.getUrls().base : "https://bitwarden.com");
                return bw_Response.success(stringRes);
            }
            // The server config cannot be updated while a user is actively logged in to the current server
            const activeAccount = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            if (activeAccount) {
                return bw_Response.error("Logout required before server config update.");
            }
            url = url === "null" || url === "bitwarden.com" || url === "https://bitwarden.com" ? null : url;
            yield this.environmentService.setEnvironment(bw_Region.SelfHosted, {
                base: url,
                webVault: options.webVault || null,
                api: options.api || null,
                identity: options.identity || null,
                icons: options.icons || null,
                notifications: options.notifications || null,
                events: options.events || null,
                keyConnector: options.keyConnector || null,
            });
            const res = new bw_MessageResponse("Saved setting `config`.", null);
            return bw_Response.success(res);
        });
    }
}

;// ../../libs/common/src/tools/public-classifier.ts
class bw_PublicClassifier {
    constructor(keys) {
        this.keys = keys;
    }
    classify(value) {
        const pickMe = JSON.parse(JSON.stringify(value));
        const picked = {};
        for (const key of this.keys) {
            picked[key] = pickMe[key];
        }
        const disclosed = picked;
        return { disclosed, secret: "" };
    }
    declassify(disclosed, _secret) {
        const result = {};
        for (const key of this.keys) {
            result[key] = disclosed[key];
        }
        return result;
    }
}

;// ../../libs/common/src/tools/state/identity-state-constraint.ts

// The constraints type shares the properties of the state,
// but never has any members
const bw_EMPTY_CONSTRAINTS = new Proxy(Object.freeze({}), {
    get() {
        return {};
    },
});
/** A constraint that does nothing. */
class bw_identity_state_constraint_IdentityConstraint {
    /** Instantiate the identity constraint */
    constructor() {
        this.constraints = bw_EMPTY_CONSTRAINTS;
    }
    calibrate() {
        return this;
    }
    adjust(state) {
        return state;
    }
    fix(state) {
        return state;
    }
}
/** Emits a constraint that does not alter the input state. */
function bw_unconstrained$() {
    const identity = new bw_identity_state_constraint_IdentityConstraint();
    const constraints$ = new bw_external_rxjs_namespaceObject.BehaviorSubject(identity);
    return constraints$;
}

;// ../../libs/tools/generator/core/src/engine/key-service-randomizer.ts
var bw_key_service_randomizer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
/** A randomizer backed by a KeyService. */
class bw_key_service_randomizer_KeyServiceRandomizer {
    /** instantiates the type.
     * @param keyService generates random numbers
     */
    constructor(keyService) {
        this.keyService = keyService;
    }
    pick(list) {
        return bw_key_service_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a;
            const length = (_a = list === null || list === void 0 ? void 0 : list.length) !== null && _a !== void 0 ? _a : 0;
            if (length <= 0) {
                throw new Error("list must have at least one entry.");
            }
            const index = yield this.uniform(0, list.length - 1);
            return list[index];
        });
    }
    pickWord(list, options) {
        return bw_key_service_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            let word = yield this.pick(list);
            if ((_a = options === null || options === void 0 ? void 0 : options.titleCase) !== null && _a !== void 0 ? _a : false) {
                word = word.charAt(0).toUpperCase() + word.slice(1);
            }
            if ((_b = options === null || options === void 0 ? void 0 : options.number) !== null && _b !== void 0 ? _b : false) {
                const num = yield this.keyService.randomNumber(1, 9);
                word = word + num.toString();
            }
            return word;
        });
    }
    // ref: https://stackoverflow.com/a/12646864/1090359
    shuffle(items, options) {
        return bw_key_service_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            const length = (_a = items === null || items === void 0 ? void 0 : items.length) !== null && _a !== void 0 ? _a : 0;
            if (length <= 0) {
                throw new Error("items must have at least one entry.");
            }
            const shuffled = ((_b = options === null || options === void 0 ? void 0 : options.copy) !== null && _b !== void 0 ? _b : true) ? [...items] : items;
            for (let i = shuffled.length - 1; i > 0; i--) {
                const j = yield this.uniform(0, i);
                [shuffled[i], shuffled[j]] = [shuffled[j], shuffled[i]];
            }
            return shuffled;
        });
    }
    chars(length) {
        return bw_key_service_randomizer_awaiter(this, void 0, void 0, function* () {
            let str = "";
            const charSet = "abcdefghijklmnopqrstuvwxyz1234567890";
            for (let i = 0; i < length; i++) {
                const randomCharIndex = yield this.uniform(0, charSet.length - 1);
                str += charSet.charAt(randomCharIndex);
            }
            return str;
        });
    }
    uniform(min, max) {
        return bw_key_service_randomizer_awaiter(this, void 0, void 0, function* () {
            return this.keyService.randomNumber(min, max);
        });
    }
}

;// ../../libs/common/src/tools/integration/integration-context.ts

/** Utilities for processing integration settings */
class bw_IntegrationContext {
    /** Instantiates an integration context
     *  @param metadata - defines integration capabilities
     *  @param i18n - localizes error messages
     */
    constructor(metadata, settings, i18n) {
        this.metadata = metadata;
        this.settings = settings;
        this.i18n = i18n;
    }
    /** Lookup the integration's baseUrl
     *  @returns the baseUrl for the API's integration point.
     *   - By default this is defined by the metadata
     *   - When a service allows self-hosting, this can be supplied by `settings`.
     *  @throws a localized error message when a base URL is neither defined by the metadata or
     *   supplied by an argument.
     */
    baseUrl() {
        var _a, _b;
        // normalize baseUrl
        const setting = (_a = (this.settings && "baseUrl" in this.settings
            ? this.settings.baseUrl
            : undefined)) !== null && _a !== void 0 ? _a : "";
        let result = "";
        // look up definition
        if (this.metadata.selfHost === "always") {
            result = setting;
        }
        else if (this.metadata.selfHost === "never" || setting.length <= 0) {
            result = (_b = this.metadata.baseUrl) !== null && _b !== void 0 ? _b : "";
        }
        else {
            result = setting;
        }
        // postconditions
        if (result === "") {
            const error = this.i18n.t("forwarderNoUrl", this.metadata.name);
            throw error;
        }
        return result;
    }
    /** look up a service API's authentication token
     *  @param options.base64 when `true`, base64 encodes the result. Defaults to `false`.
     *  @param options.suffix a string to append to the token. Defaults to empty.
     *  @returns the user's authentication token
     *  @throws a localized error message when the token is invalid.
     *  @remarks the string is thrown for backwards compatibility
     */
    authenticationToken(options = null) {
        var _a, _b;
        // normalize `token` then assert it has a value
        let token = "token" in this.settings ? ((_a = this.settings.token) !== null && _a !== void 0 ? _a : "") : "";
        if (token === "") {
            const error = this.i18n.t("forwaderInvalidToken", this.metadata.name);
            throw error;
        }
        // if a suffix exists, it needs to be included before encoding
        token += (_b = options === null || options === void 0 ? void 0 : options.suffix) !== null && _b !== void 0 ? _b : "";
        if (options === null || options === void 0 ? void 0 : options.base64) {
            token = bw_utils_Utils.fromUtf8ToB64(token);
        }
        return token;
    }
    /** look up the website the integration is working with.
     *  @param request supplies information about the state of the extension site
     *  @returns The website or an empty string if a website isn't available
     *  @remarks `website` is usually supplied when generating a credential from the vault
     */
    website(request) {
        var _a;
        return (_a = request.website) !== null && _a !== void 0 ? _a : "";
    }
    /** look up localized text indicating Bitwarden requested the forwarding address.
     *  @param request supplies information about the state of the extension site
     *  @returns localized text describing a generated forwarding address
     */
    generatedBy(request) {
        const website = this.website(request);
        const descriptionId = website === "" ? "forwarderGeneratedBy" : "forwarderGeneratedByWithWebsite";
        const description = this.i18n.t(descriptionId, website);
        return description;
    }
}

;// ../../libs/tools/generator/core/src/engine/forwarder-context.ts

/**
 * Surfaces contextual information to forwarder integrations.
 */
class bw_forwarder_context_ForwarderContext extends bw_IntegrationContext {
    /** Instantiates the context.
     * @param configuration of the forwarder this context assists
     * @param settings loaded from the forwarder's state
     * @param i18n localizes error handling
     */
    constructor(configuration, settings, i18n) {
        super(configuration, settings, i18n);
        this.configuration = configuration;
    }
    /** look up the domain part of an email address from the forwarder's settings.
     *  @returns a domain part of an email address
     *  @throws a localized error message when the domain isn't found.
     *  @remarks the string is thrown for backwards compatibility
     */
    emailDomain() {
        var _a;
        const domain = "domain" in this.settings ? ((_a = this.settings.domain) !== null && _a !== void 0 ? _a : "") : "";
        if (domain === "") {
            const error = this.i18n.t("forwarderNoDomain", this.configuration.name);
            throw error;
        }
        return domain;
    }
    /** look up a prefix applied to the email address from the forwarder's settings.
     *  @returns the prefix
     *  @throws a localized error message when the prefix isn't found.
     *  @remarks the string is thrown for backwards compatibility
     */
    emailPrefix() {
        var _a;
        const prefix = "prefix" in this.settings ? ((_a = this.settings.prefix) !== null && _a !== void 0 ? _a : "") : "";
        if (prefix === "") {
            const error = this.i18n.t("forwarderNoPrefix", this.configuration.name);
            throw error;
        }
        return prefix;
    }
    /** look up a localized error message indicating an account id is required
     *  but wasn't found.
     *  @remarks this returns a string instead of throwing it so that the
     *    user can decide upon control flow.
     */
    missingAccountIdCause() {
        return this.i18n.t("forwarderNoAccountId", this.configuration.name);
    }
}

;// ../../libs/tools/generator/core/src/types/generated-credential.ts
/** A credential generation result */
class bw_generated_credential_GeneratedCredential {
    /**
     * Instantiates a generated credential
     * @param credential The value of the generated credential (e.g. a password)
     * @param category The kind of credential
     * @param generationDate The date that the credential was generated.
     *   Numeric values should are interpreted using {@link Date.valueOf}
     *   semantics.
     * @param source traces the origin of the request that generated this credential.
     * @param website traces the website associated with the generated credential.
     */
    constructor(credential, category, generationDate, source, website) {
        this.credential = credential;
        this.category = category;
        this.source = source;
        this.website = website;
        if (typeof generationDate === "number") {
            this.generationDate = new Date(generationDate);
        }
        else {
            this.generationDate = generationDate;
        }
    }
    /** Constructs a credential from its `toJSON` representation */
    static fromJSON(jsonValue) {
        return new bw_generated_credential_GeneratedCredential(jsonValue.credential, jsonValue.category, jsonValue.generationDate);
    }
    /** Serializes a credential to a JSON-compatible object */
    toJSON() {
        // omits the source and website because they were introduced to solve
        // UI bugs and it's not yet known whether there's a desire to support
        // them in the generator history view.
        return {
            credential: this.credential,
            category: this.category,
            generationDate: this.generationDate.valueOf(),
        };
    }
}

;// ../../libs/tools/generator/core/src/data/generator-types.ts
/** Types of passwords that may be generated by the credential generator */
const bw_generator_types_PasswordAlgorithms = Object.freeze(["password", "passphrase"]);
/** Types of usernames that may be generated by the credential generator */
const bw_generator_types_UsernameAlgorithms = Object.freeze(["username"]);
/** Types of email addresses that may be generated by the credential generator */
const bw_generator_types_EmailAlgorithms = Object.freeze(["catchall", "subaddress"]);
/** All types of credentials that may be generated by the credential generator */
const bw_CredentialAlgorithms = Object.freeze([
    ...bw_generator_types_PasswordAlgorithms,
    ...bw_generator_types_UsernameAlgorithms,
    ...bw_generator_types_EmailAlgorithms,
]);

;// ../../libs/tools/generator/core/src/types/generator-type.ts

/** Returns true when the input algorithm is a forwarder integration. */
function bw_generator_type_isForwarderIntegration(algorithm) {
    return algorithm && typeof algorithm === "object" && "forwarder" in algorithm;
}
function bw_isSameAlgorithm(lhs, rhs) {
    if (lhs === rhs) {
        return true;
    }
    else if (bw_generator_type_isForwarderIntegration(lhs) && bw_generator_type_isForwarderIntegration(rhs)) {
        return lhs.forwarder === rhs.forwarder;
    }
    else {
        return false;
    }
}
/** Compound credential types supported by the credential generator. */
const bw_generator_type_CredentialCategories = Object.freeze({
    /** Lists algorithms in the "password" credential category */
    password: bw_generator_types_PasswordAlgorithms,
    /** Lists algorithms in the "username" credential category */
    username: bw_generator_types_UsernameAlgorithms,
    /** Lists algorithms in the "email" credential category */
    email: bw_generator_types_EmailAlgorithms,
});
/** Returns true when the input algorithm is a password algorithm. */
function bw_isPasswordAlgorithm(algorithm) {
    return PasswordAlgorithms.includes(algorithm);
}
/** Returns true when the input algorithm is a username algorithm. */
function bw_isUsernameAlgorithm(algorithm) {
    return UsernameAlgorithms.includes(algorithm);
}
/** Returns true when the input algorithm is an email algorithm. */
function bw_isEmailAlgorithm(algorithm) {
    return EmailAlgorithms.includes(algorithm) || bw_generator_type_isForwarderIntegration(algorithm);
}

;// ../../libs/tools/generator/core/src/types/index.ts




















;// ../../libs/tools/generator/core/src/engine/data.ts
function bw_toCharacterSet(characters) {
    const set = characters.split("");
    return Object.freeze(set);
}
const bw_SpecialCharacters = bw_toCharacterSet("!@#$%^&*");
/** Sets of Ascii characters used for password generation */
const bw_Ascii = Object.freeze({
    /** The full set of characters available to the generator */
    Full: Object.freeze({
        Uppercase: bw_toCharacterSet("ABCDEFGHIJKLMNOPQRSTUVWXYZ"),
        Lowercase: bw_toCharacterSet("abcdefghijklmnopqrstuvwxyz"),
        Digit: bw_toCharacterSet("0123456789"),
        Special: bw_SpecialCharacters,
    }),
    /** All characters available to the generator that are not ambiguous. */
    Unmistakable: Object.freeze({
        Uppercase: bw_toCharacterSet("ABCDEFGHJKLMNPQRSTUVWXYZ"),
        Lowercase: bw_toCharacterSet("abcdefghijkmnopqrstuvwxyz"),
        Digit: bw_toCharacterSet("23456789"),
        Special: bw_SpecialCharacters,
    }),
});
/** Splits an email into a username, subaddress, and domain named group.
 * Subaddress is optional.
 */
const bw_SUBADDRESS_PARSER = new RegExp("(?<username>[^@+]+)(?<subaddress>\\+.+)?(?<domain>@.+)");

;// ../../libs/tools/generator/core/src/engine/email-randomizer.ts
var bw_email_randomizer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



/** Generation algorithms that produce randomized email addresses */
class bw_EmailRandomizer {
    /** Instantiates the email randomizer
     *  @param random data source for random data
     */
    constructor(random) {
        this.random = random;
    }
    /** Appends a random set of characters as a subaddress
     *  @param email the email address used to generate a subaddress. If this address
     *    already contains a subaddress, the subaddress is extended.
     *  @param options.length the number of characters to append to the subaddress. Defaults to 8. If
     *    the length is <= 0, the function returns the input address.
     *  @returns a promise that resolves with the generated email address. If the provided address
     *    lacks a username (the part before the "@") or domain (the part after the "@"), the function
     *    returns the input address.
     */
    randomAsciiSubaddress(email, options) {
        return bw_email_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            let result = email !== null && email !== void 0 ? email : "";
            const subaddressLength = (_a = options === null || options === void 0 ? void 0 : options.length) !== null && _a !== void 0 ? _a : 8;
            if (subaddressLength < 1) {
                return result;
            }
            const parsed = bw_SUBADDRESS_PARSER.exec(result);
            if (!parsed) {
                return result;
            }
            let subaddress = (_b = parsed.groups.subaddress) !== null && _b !== void 0 ? _b : "+";
            subaddress += yield this.random.chars(subaddressLength);
            result = `${parsed.groups.username}${subaddress}${parsed.groups.domain}`;
            return result;
        });
    }
    /** Creates a catchall address composed of random characters
     *  @param domain the domain part of the generated email address.
     *  @param options.length the number of characters to include in the catchall
     *    address. Defaults to 8.
     *  @returns a promise that resolves with the generated email address. If the domain
     *    is empty, resolves to null instead.
     */
    randomAsciiCatchall(domain, options) {
        return bw_email_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a;
            const emailDomain = (domain === null || domain === void 0 ? void 0 : domain.startsWith("@")) ? domain.substring(1, Infinity) : (domain !== null && domain !== void 0 ? domain : "");
            if (emailDomain.length < 1) {
                return null;
            }
            const length = (_a = options === null || options === void 0 ? void 0 : options.length) !== null && _a !== void 0 ? _a : 8;
            if (length < 1) {
                return null;
            }
            const catchall = yield this.random.chars(length);
            const result = `${catchall}@${domain}`;
            return result;
        });
    }
    /** Creates a catchall address composed of random words
     *  @param domain the domain part of the generated email address.
     *  @param options.numberOfWords the number of words to include in the catchall
     *    address. Defaults to 1.
     *  @param options.words selects words from the provided wordlist. Defaults to
     *    the EFF "5-dice" list.
     *  @returns a promise that resolves with the generated email address.
     */
    randomWordsCatchall(domain, options) {
        return bw_email_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            const emailDomain = (domain === null || domain === void 0 ? void 0 : domain.startsWith("@")) ? domain.substring(1, Infinity) : (domain !== null && domain !== void 0 ? domain : "");
            if (emailDomain.length < 1) {
                return null;
            }
            const numberOfWords = (_a = options === null || options === void 0 ? void 0 : options.numberOfWords) !== null && _a !== void 0 ? _a : 1;
            if (numberOfWords < 1) {
                return null;
            }
            const wordList = (_b = options === null || options === void 0 ? void 0 : options.words) !== null && _b !== void 0 ? _b : bw_EFFLongWordList;
            const words = [];
            for (let i = 0; i < numberOfWords; i++) {
                // camelCase the words for legibility
                words[i] = yield this.random.pickWord(wordList, { titleCase: i !== 0 });
            }
            const result = `${words.join("")}@${domain}`;
            return result;
        });
    }
    generate(request, settings) {
        return bw_email_randomizer_awaiter(this, void 0, void 0, function* () {
            if (bw_isCatchallGenerationOptions(settings)) {
                const email = yield this.randomAsciiCatchall(settings.catchallDomain);
                return new bw_generated_credential_GeneratedCredential(email, "catchall", Date.now(), request.source, request.website);
            }
            else if (bw_isSubaddressGenerationOptions(settings)) {
                const email = yield this.randomAsciiSubaddress(settings.subaddressEmail);
                return new bw_generated_credential_GeneratedCredential(email, "subaddress", Date.now(), request.source, request.website);
            }
            throw new Error("Invalid settings received by generator.");
        });
    }
}
function bw_isCatchallGenerationOptions(settings) {
    return "catchallDomain" in (settings !== null && settings !== void 0 ? settings : {});
}
function bw_isSubaddressGenerationOptions(settings) {
    return "subaddressEmail" in (settings !== null && settings !== void 0 ? settings : {});
}

;// ../../libs/tools/generator/core/src/engine/email-calculator.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/** Generation algorithms that produce deterministic email addresses */
class bw_EmailCalculator {
    /**
     * Appends appendText to the subaddress of an email address.
     * @param appendText  The calculation fails if this is shorter than 1 character
     *   long, undefined, or null.
     * @param email the email address to alter.
     * @returns `email` with `appendText` added to its subaddress (the part
     *   following the "+"). If there is no subaddress, a subaddress is created.
     *   If the email address fails to parse, it is returned unaltered.
     */
    appendToSubaddress(appendText, email) {
        var _a;
        let result = (email !== null && email !== void 0 ? email : "").trim();
        const suffix = (appendText !== null && appendText !== void 0 ? appendText : "").trim();
        if (suffix.length < 1) {
            return result;
        }
        const parsed = bw_SUBADDRESS_PARSER.exec(result);
        if (!parsed) {
            return result;
        }
        const subaddress = ((_a = parsed.groups.subaddress) !== null && _a !== void 0 ? _a : "+") + suffix;
        result = `${parsed.groups.username}${subaddress}${parsed.groups.domain}`;
        return result;
    }
    /**
     * Derives an email address from a username and domain name.
     * @param username the username part of the email address. The calculation fails if this is
     *   shorter than 1 character long, undefined, or null.
     * @param domain the domain part of the email address. The calculation fails if this is empty,
     *   undefined, or null.
     * @returns an email address or `null` if the calculation fails.
     */
    concatenate(username, domain) {
        const emailDomain = (domain === null || domain === void 0 ? void 0 : domain.startsWith("@")) ? domain.substring(1, Infinity) : (domain !== null && domain !== void 0 ? domain : "");
        if (emailDomain.length < 1) {
            return null;
        }
        const emailWebsite = username !== null && username !== void 0 ? username : "";
        if (emailWebsite.length < 1) {
            return null;
        }
        const result = `${emailWebsite}@${emailDomain}`;
        return result;
    }
}

;// ../../libs/tools/generator/core/src/util.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/** construct a method that outputs a copy of `defaultValue` as an observable. */
function bw_observe$PerUserId(create) {
    const _subjects = new Map();
    return (key) => {
        let value = _subjects.get(key);
        if (value === undefined) {
            const initialValue = create();
            value = new bw_external_rxjs_namespaceObject.BehaviorSubject(Object.assign({}, initialValue));
            _subjects.set(key, value);
        }
        return value.asObservable();
    };
}
/** construct a method that caches user-specific states by userid. */
function bw_sharedByUserId(create) {
    const _subjects = new Map();
    return (key) => {
        let value = _subjects.get(key);
        if (value === undefined) {
            value = create(key);
            _subjects.set(key, value);
        }
        return value;
    };
}
/** construct a method that loads a user-specific state from the provider. */
function bw_sharedStateByUserId(key, provider) {
    return (id) => provider.getUser(id, key);
}
/** returns the sum of items in the list. */
const bw_sum = (...items) => (items !== null && items !== void 0 ? items : []).reduce((sum, current) => sum + (current !== null && current !== void 0 ? current : 0), 0);
/* converts password generation option sets, which are defined by
 * an "enabled" and "quantity" parameter, to the password engine's
 * parameters, which represent disabled options as `undefined`
 * properties.
 */
function bw_optionsToRandomAsciiRequest(options) {
    var _a, _b;
    // helper for processing common option sets
    function process(
    // values read from the options
    enabled, quantity, 
    // value used if an option is missing
    defaultEnabled, defaultQuantity) {
        const isEnabled = enabled !== null && enabled !== void 0 ? enabled : defaultEnabled;
        const actualQuantity = quantity !== null && quantity !== void 0 ? quantity : defaultQuantity;
        const result = isEnabled ? actualQuantity : undefined;
        return result;
    }
    const request = {
        uppercase: process(options.uppercase, options.minUppercase, bw_DefaultPasswordGenerationOptions.uppercase, bw_DefaultPasswordGenerationOptions.minUppercase),
        lowercase: process(options.lowercase, options.minLowercase, bw_DefaultPasswordGenerationOptions.lowercase, bw_DefaultPasswordGenerationOptions.minLowercase),
        digits: process(options.number, options.minNumber, bw_DefaultPasswordGenerationOptions.number, bw_DefaultPasswordGenerationOptions.minNumber),
        special: process(options.special, options.minSpecial, bw_DefaultPasswordGenerationOptions.special, bw_DefaultPasswordGenerationOptions.minSpecial),
        ambiguous: (_a = options.ambiguous) !== null && _a !== void 0 ? _a : bw_DefaultPasswordGenerationOptions.ambiguous,
        all: 0,
    };
    // engine represents character sets as "include only"; you assert how many all
    // characters there can be rather than a total length. This conversion has
    // the character classes win, so that the result is always consistent with policy
    // minimums.
    const required = bw_sum(request.uppercase, request.lowercase, request.digits, request.special);
    const remaining = ((_b = options.length) !== null && _b !== void 0 ? _b : 0) - required;
    request.all = Math.max(remaining, 0);
    return request;
}
/* converts passphrase generation option sets to the eff word list request
 */
function bw_optionsToEffWordListRequest(options) {
    var _a, _b, _c, _d;
    const requestWords = (_a = options.numWords) !== null && _a !== void 0 ? _a : bw_DefaultPassphraseGenerationOptions.numWords;
    const request = {
        numberOfWords: Math.max(requestWords, bw_DefaultPassphraseBoundaries.numWords.min),
        capitalize: (_b = options.capitalize) !== null && _b !== void 0 ? _b : bw_DefaultPassphraseGenerationOptions.capitalize,
        number: (_c = options.includeNumber) !== null && _c !== void 0 ? _c : bw_DefaultPassphraseGenerationOptions.includeNumber,
        separator: (_d = options.wordSeparator) !== null && _d !== void 0 ? _d : bw_DefaultPassphraseGenerationOptions.wordSeparator,
    };
    return request;
}

;// ../../libs/tools/generator/core/src/engine/password-randomizer.ts
var bw_password_randomizer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




/** Generation algorithms that produce randomized secrets */
class bw_PasswordRandomizer {
    /** Instantiates the password randomizer
     *  @param randomizer data source for random data
     */
    constructor(randomizer) {
        this.randomizer = randomizer;
    }
    /** create a password from ASCII codepoints
     *  @param request refines the generated password
     *  @returns a promise that completes with the generated password
     */
    randomAscii(request) {
        return bw_password_randomizer_awaiter(this, void 0, void 0, function* () {
            // randomize character sets
            const sets = bw_toAsciiSets(request);
            const shuffled = yield this.randomizer.shuffle(sets);
            // generate password
            const generating = shuffled.flatMap((set) => this.randomizer.pick(set));
            const generated = yield Promise.all(generating);
            const result = generated.join("");
            return result;
        });
    }
    /** create a passphrase from the EFF's "5 dice" word list
     *  @param request refines the generated passphrase
     * @returns a promise that completes with the generated passphrase
     */
    randomEffLongWords(request) {
        return bw_password_randomizer_awaiter(this, void 0, void 0, function* () {
            // select which word gets the number, if any
            let luckyNumber = -1;
            if (request.number) {
                luckyNumber = yield this.randomizer.uniform(0, request.numberOfWords - 1);
            }
            // generate the passphrase
            const wordList = new Array(request.numberOfWords);
            for (let i = 0; i < request.numberOfWords; i++) {
                const word = yield this.randomizer.pickWord(bw_EFFLongWordList, {
                    titleCase: request.capitalize,
                    number: i === luckyNumber,
                });
                wordList[i] = word;
            }
            return wordList.join(request.separator);
        });
    }
    generate(request, settings) {
        return bw_password_randomizer_awaiter(this, void 0, void 0, function* () {
            if (bw_isPasswordGenerationOptions(settings)) {
                const req = bw_optionsToRandomAsciiRequest(settings);
                const password = yield this.randomAscii(req);
                return new bw_generated_credential_GeneratedCredential(password, "password", Date.now(), request.source, request.website);
            }
            else if (bw_isPassphraseGenerationOptions(settings)) {
                const req = bw_optionsToEffWordListRequest(settings);
                const passphrase = yield this.randomEffLongWords(req);
                return new bw_generated_credential_GeneratedCredential(passphrase, "passphrase", Date.now(), request.source, request.website);
            }
            throw new Error("Invalid settings received by generator.");
        });
    }
}
function bw_isPasswordGenerationOptions(settings) {
    return "length" in (settings !== null && settings !== void 0 ? settings : {});
}
function bw_isPassphraseGenerationOptions(settings) {
    return "numWords" in (settings !== null && settings !== void 0 ? settings : {});
}
// given a generator request, convert each of its `number | undefined` properties
// to an array of character sets, one for each property. The transformation is
// deterministic.
function bw_toAsciiSets(request) {
    // allocate an array and initialize each cell with a fixed value
    function allocate(size, value) {
        const data = new Array(size > 0 ? size : 0);
        data.fill(value, 0, size);
        return data;
    }
    const allSet = [];
    const active = request.ambiguous ? bw_Ascii.Full : bw_Ascii.Unmistakable;
    const parts = [];
    if (request.uppercase !== undefined) {
        parts.push(...allocate(request.uppercase, active.Uppercase));
        allSet.push(...active.Uppercase);
    }
    if (request.lowercase !== undefined) {
        parts.push(...allocate(request.lowercase, active.Lowercase));
        allSet.push(...active.Lowercase);
    }
    if (request.digits !== undefined) {
        parts.push(...allocate(request.digits, active.Digit));
        allSet.push(...active.Digit);
    }
    if (request.special !== undefined) {
        parts.push(...allocate(request.special, active.Special));
        allSet.push(...active.Special);
    }
    parts.push(...allocate(request.all, allSet));
    return parts;
}

;// ../../libs/tools/generator/core/src/engine/username-randomizer.ts
var bw_username_randomizer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


/** The number of digits used when generating an Eff username with a number. */
const bw_NUMBER_OF_DIGITS = 4;
/** Generation algorithms that produce randomized usernames */
class bw_UsernameRandomizer {
    /** Instantiates the username randomizer
     *  @param random data source for random data
     */
    constructor(random) {
        this.random = random;
    }
    /** Creates a username composed of random words
     *  @param request parameters to which the generated username conforms
     *  @returns a promise that resolves with the generated username.
     */
    randomWords(request) {
        return bw_username_randomizer_awaiter(this, void 0, void 0, function* () {
            var _a, _b, _c;
            const numberOfWords = (_a = request === null || request === void 0 ? void 0 : request.numberOfWords) !== null && _a !== void 0 ? _a : 1;
            if (numberOfWords < 1) {
                return "";
            }
            const digits = Math.max((_b = request === null || request === void 0 ? void 0 : request.digits) !== null && _b !== void 0 ? _b : 0, 0);
            let selectCase = (_) => false;
            if ((request === null || request === void 0 ? void 0 : request.casing) === "camelCase") {
                selectCase = (i) => i !== 0;
            }
            else if ((request === null || request === void 0 ? void 0 : request.casing) === "TitleCase") {
                selectCase = (_) => true;
            }
            const wordList = (_c = request === null || request === void 0 ? void 0 : request.words) !== null && _c !== void 0 ? _c : bw_EFFLongWordList;
            const parts = [];
            for (let i = 0; i < numberOfWords; i++) {
                const word = yield this.random.pickWord(wordList, { titleCase: selectCase(i) });
                parts.push(word);
            }
            for (let i = 0; i < digits; i++) {
                const digit = yield this.random.uniform(0, 9);
                parts.push(digit.toString());
            }
            const result = parts.join("");
            return result;
        });
    }
    generate(request, settings) {
        return bw_username_randomizer_awaiter(this, void 0, void 0, function* () {
            if (bw_isEffUsernameGenerationOptions(settings)) {
                const username = yield this.randomWords({
                    digits: settings.wordIncludeNumber ? bw_NUMBER_OF_DIGITS : 0,
                    casing: settings.wordCapitalize ? "TitleCase" : "lowercase",
                });
                return new bw_generated_credential_GeneratedCredential(username, "username", Date.now(), request.source, request.website);
            }
            throw new Error("Invalid settings received by generator.");
        });
    }
}
function bw_isEffUsernameGenerationOptions(settings) {
    return "wordIncludeNumber" in (settings !== null && settings !== void 0 ? settings : {});
}

;// ../../libs/tools/generator/core/src/engine/index.ts








;// ../../libs/tools/generator/core/src/engine/forwarder.ts
var bw_forwarder_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



/** Generation algorithms that query an email forwarding service to
 *  create anonymized email addresses.
 */
class bw_forwarder_Forwarder {
    /** Instantiates the email forwarder engine
     *  @param configuration The forwarder to query
     *  @param client requests data from the forwarding service
     *  @param i18nService localizes messages sent to the forwarding service
     *   and user-addressable errors
     */
    constructor(configuration, client, i18nService) {
        this.configuration = configuration;
        this.client = client;
        this.i18nService = i18nService;
    }
    generate(request, settings) {
        return bw_forwarder_awaiter(this, void 0, void 0, function* () {
            const requestOptions = { website: request.website };
            const getAccount = yield this.getAccountId(this.configuration, settings);
            if (getAccount) {
                requestOptions.accountId = yield this.client.fetchJson(getAccount, requestOptions);
            }
            const create = this.createForwardingAddress(this.configuration, settings);
            const result = yield this.client.fetchJson(create, requestOptions);
            const id = { forwarder: this.configuration.id };
            return new GeneratedCredential(result, id, Date.now());
        });
    }
    createContext(configuration, settings) {
        return new ForwarderContext(configuration, settings, this.i18nService);
    }
    createForwardingAddress(configuration, settings) {
        const context = this.createContext(configuration, settings);
        const rpc = new CreateForwardingAddressRpc(configuration, context);
        return rpc;
    }
    getAccountId(configuration, settings) {
        if (!configuration.forwarder.getAccountId) {
            return null;
        }
        const context = this.createContext(configuration, settings);
        const rpc = new GetAccountIdRpc(configuration, context);
        return rpc;
    }
}

;// ../../libs/tools/generator/core/src/policies/default-policy-evaluator.ts
/** A policy evaluator that does not apply any policy */
class bw_default_policy_evaluator_DefaultPolicyEvaluator {
    /** {@link PolicyEvaluator.policy} */
    get policy() {
        return {};
    }
    /** {@link PolicyEvaluator.policyInEffect} */
    get policyInEffect() {
        return false;
    }
    /** {@link PolicyEvaluator.applyPolicy} */
    applyPolicy(options) {
        return options;
    }
    /** {@link PolicyEvaluator.sanitize} */
    sanitize(options) {
        return options;
    }
}

;// ../../libs/tools/generator/core/src/policies/constraints.ts

const bw_Zero = { min: 0, max: 0 };
const bw_AtLeastOne = { min: 1 };
const bw_RequiresTrue = { requiredValue: true };
/** Ensures the minimum and maximum bounds of a constraint are at least as large as the
 *  combined minimum bounds of `dependencies`.
 *  @param current the constraint extended by the combinator.
 *  @param dependencies the constraints summed to determine the bounds of `current`.
 *  @returns a copy of `current` with the new bounds applied.
 *
 */
function bw_atLeastSum(current, dependencies) {
    var _a;
    // length must be at least as long as the required character set
    const minConsistentLength = bw_sum(...dependencies.map((c) => c === null || c === void 0 ? void 0 : c.min));
    const minLength = Math.max((_a = current === null || current === void 0 ? void 0 : current.min) !== null && _a !== void 0 ? _a : 0, minConsistentLength);
    const length = bw_atLeast(minLength, current);
    return length;
}
/** Extends a constraint with a readonly field.
 *  @param readonly Adds a readonly field when this is `true`.
 *  @param constraint the constraint extended by the combinator.
 *  @returns a copy of `constraint` with the readonly constraint applied as-needed.
 */
function bw_maybeReadonly(readonly, constraint) {
    if (!readonly) {
        return constraint;
    }
    const result = Object.assign({}, constraint !== null && constraint !== void 0 ? constraint : {});
    result.readonly = true;
    return result;
}
/** Conditionally enables a constraint.
 *  @param enabled the condition to evaluate
 *  @param constraint the condition to conditionally enable
 *  @returns `constraint` when `enabled` is true. Otherwise returns `undefined.
 */
function bw_maybe(enabled, constraint) {
    return enabled ? constraint : undefined;
}
// copies `constraint`; ensures both bounds >= value
/** Ensures the boundaries of a constraint are at least equal to the minimum.
 *  @param minimum the lower bound of the constraint. When this is `undefined` or `null`,
 *   the method returns `constraint`.
 *  @param constraint the constraint to evaluate. When this is `undefined` or `null`,
 *   the method creates a new constraint.
 *  @returns a copy of `constraint`. When `minimum` has a value, the returned constraint
 *   always includes a minimum bound. When `constraint` has a maximum defined, both
 *   its minimum and maximum are checked against `minimum`.
 */
function bw_atLeast(minimum, constraint) {
    var _a;
    if (minimum === undefined || minimum === null) {
        return constraint;
    }
    const atLeast = Object.assign({}, (constraint !== null && constraint !== void 0 ? constraint : {}));
    atLeast.min = Math.max((_a = atLeast.min) !== null && _a !== void 0 ? _a : -Infinity, minimum);
    if ("max" in atLeast) {
        atLeast.max = Math.max(atLeast.max, minimum);
    }
    return atLeast;
}
/** Ensures a value falls within the minimum and maximum boundaries of a constraint.
 *  @param value the value to check. Nullish values are coerced to 0.
 *  @param constraint the constraint to evaluate against.
 *  @returns If the value is below the minimum constraint, the minimum bound is
 *   returned. If the value is above the maximum constraint, the maximum bound is
 *   returned. Otherwise, the value is returned.
 */
function bw_fitToBounds(value, constraint) {
    if (!constraint) {
        return value;
    }
    const { min, max } = constraint;
    const withUpperBound = Math.min(value !== null && value !== void 0 ? value : 0, max !== null && max !== void 0 ? max : Infinity);
    const withLowerBound = Math.max(withUpperBound, min !== null && min !== void 0 ? min : -Infinity);
    return withLowerBound;
}
/** Fits the length of a string within the minimum and maximum length boundaries
 *  of a constraint.
 *  @param value the value to check. Nullish values are coerced to the empty string.
 *  @param constraint the constraint to evaluate against.
 *  @param options.fillString a string to fill values from. Defaults to a space.
 *   When fillString contains multiple characters, each is filled in order. The
 *   fill string repeats when it gets to the end of the string and there are
 *   more characters to fill.
 *  @returns If the value is below the required length, returns a copy padded
 *   by the fillString. If the value is above the required length, returns a copy
 *   padded to the maximum length.
 * */
function bw_fitLength(value, constraint, options) {
    if (!constraint) {
        return value;
    }
    const { minLength, maxLength } = constraint;
    const { fillString } = options !== null && options !== void 0 ? options : { fillString: " " };
    const trimmed = (value !== null && value !== void 0 ? value : "").slice(0, maxLength !== null && maxLength !== void 0 ? maxLength : Infinity);
    const result = trimmed.padEnd(minLength !== null && minLength !== void 0 ? minLength : trimmed.length, fillString);
    return result;
}
/** Enforces a readonly field has a required value.
 *  @param value the value to check.
 *  @param constraint the constraint to evaluate against.
 *  @returns If the constraint's readonly field is `true`, returns the
 *   constraint's required value or `undefined` if none is specified.
 *   Otherwise returns the value.
 *  @remarks This method can be used to ensure a conditionally-calculated
 *   field becomes undefined. Simply specify `readonly` without a `requiredValue`
 *   then use `??` to perform the calculation.
 */
function bw_enforceConstant(value, constraint) {
    if (constraint === null || constraint === void 0 ? void 0 : constraint.readonly) {
        return constraint.requiredValue;
    }
    else {
        return value;
    }
}
/** Conditionally create a readonly true value.
 *  @param enabled When true, create the value.
 *  @returns When enabled is true, a readonly constraint with a constant value
 *  of `true`. Otherwise returns `undefined`.
 */
function bw_readonlyTrueWhen(enabled) {
    const readonlyValue = bw_maybeReadonly(enabled, bw_RequiresTrue);
    const maybeReadonlyValue = bw_maybe(enabled, readonlyValue);
    return maybeReadonlyValue;
}


;// ../../libs/tools/generator/core/src/policies/password-policy-constraints.ts


class bw_PasswordPolicyConstraints {
    /** Creates a password policy constraints
     *  @param constraints Constraints derived from the policy and application-defined defaults
     */
    constructor(constraints) {
        this.constraints = constraints;
    }
    adjust(state) {
        // constrain values
        const result = Object.assign(Object.assign({}, (state !== null && state !== void 0 ? state : bw_DefaultPasswordGenerationOptions)), { length: bw_fitToBounds(state.length, this.constraints.length), lowercase: bw_enforceConstant(state.lowercase, this.constraints.lowercase), uppercase: bw_enforceConstant(state.uppercase, this.constraints.uppercase), number: bw_enforceConstant(state.number, this.constraints.number), special: bw_enforceConstant(state.special, this.constraints.special), minLowercase: bw_fitToBounds(state.minLowercase, this.constraints.minLowercase), minUppercase: bw_fitToBounds(state.minUppercase, this.constraints.minUppercase), minNumber: bw_fitToBounds(state.minNumber, this.constraints.minNumber), minSpecial: bw_fitToBounds(state.minSpecial, this.constraints.minSpecial) });
        // ensure include flags are consistent with the constrained values
        result.lowercase || (result.lowercase = state.minLowercase > 0);
        result.uppercase || (result.uppercase = state.minUppercase > 0);
        result.number || (result.number = state.minNumber > 0);
        result.special || (result.special = state.minSpecial > 0);
        // when all flags are disabled, enable a few
        const anyEnabled = [result.lowercase, result.uppercase, result.number, result.special].some((flag) => flag);
        if (!anyEnabled) {
            result.lowercase = true;
            result.uppercase = true;
        }
        return result;
    }
    fix(state) {
        return state;
    }
}

;// ../../libs/tools/generator/core/src/policies/dynamic-password-policy-constraints.ts


/** Creates state constraints by blending policy and password settings. */
class bw_DynamicPasswordPolicyConstraints {
    /** Instantiates the object.
     *  @param policy the password policy to enforce. This cannot be
     *  `null` or `undefined`.
     */
    constructor(policy, defaults) {
        this.defaults = defaults;
        const minLowercase = bw_maybe(policy.useLowercase, bw_AtLeastOne);
        const minUppercase = bw_maybe(policy.useUppercase, bw_AtLeastOne);
        const minNumber = bw_atLeast(policy.numberCount || (policy.useNumbers && bw_AtLeastOne.min), defaults.minNumber);
        const minSpecial = bw_atLeast(policy.specialCount || (policy.useSpecial && bw_AtLeastOne.min), defaults.minSpecial);
        const baseLength = bw_atLeast(policy.minLength, defaults.length);
        const subLengths = [minLowercase, minUppercase, minNumber, minSpecial];
        const length = bw_atLeastSum(baseLength, subLengths);
        this.constraints = Object.freeze({
            policyInEffect: bw_policyInEffect(policy, defaults),
            lowercase: bw_readonlyTrueWhen(policy.useLowercase),
            uppercase: bw_readonlyTrueWhen(policy.useUppercase),
            number: bw_readonlyTrueWhen(policy.useNumbers),
            special: bw_readonlyTrueWhen(policy.useSpecial),
            length,
            minLowercase,
            minUppercase,
            minNumber,
            minSpecial,
        });
    }
    calibrate(state) {
        var _a, _b, _c, _d, _e, _f, _g, _h;
        // decide which constraints are active
        const lowercase = state.lowercase || ((_a = this.constraints.lowercase) === null || _a === void 0 ? void 0 : _a.requiredValue) || false;
        const uppercase = state.uppercase || ((_b = this.constraints.uppercase) === null || _b === void 0 ? void 0 : _b.requiredValue) || false;
        const number = state.number || ((_c = this.constraints.number) === null || _c === void 0 ? void 0 : _c.requiredValue) || false;
        const special = state.special || ((_d = this.constraints.special) === null || _d === void 0 ? void 0 : _d.requiredValue) || false;
        // minimum constraints cannot `atLeast(state...) because doing so would force
        // the constrained value to only increase
        const constraints = Object.assign(Object.assign({}, this.constraints), { minLowercase: bw_maybe(lowercase, (_e = this.constraints.minLowercase) !== null && _e !== void 0 ? _e : bw_AtLeastOne), minUppercase: bw_maybe(uppercase, (_f = this.constraints.minUppercase) !== null && _f !== void 0 ? _f : bw_AtLeastOne), minNumber: (_g = bw_maybe(number, this.constraints.minNumber)) !== null && _g !== void 0 ? _g : bw_Zero, minSpecial: (_h = bw_maybe(special, this.constraints.minSpecial)) !== null && _h !== void 0 ? _h : bw_Zero });
        // lower bound of length must always at least fit its sub-lengths
        constraints.length = bw_atLeastSum(this.constraints.length, [
            bw_atLeast(state.minNumber, constraints.minNumber),
            bw_atLeast(state.minSpecial, constraints.minSpecial),
            bw_atLeast(state.minLowercase, constraints.minLowercase),
            bw_atLeast(state.minUppercase, constraints.minUppercase),
        ]);
        const stateConstraints = new bw_PasswordPolicyConstraints(constraints);
        return stateConstraints;
    }
}
function bw_policyInEffect(policy, defaults) {
    const policies = [
        policy.useUppercase,
        policy.useLowercase,
        policy.useNumbers,
        policy.useSpecial,
        policy.minLength > defaults.length.min,
        policy.numberCount > defaults.minNumber.min,
        policy.specialCount > defaults.minSpecial.min,
    ];
    return policies.includes(true);
}

;// ../../libs/tools/generator/core/src/policies/passphrase-generator-options-evaluator.ts

/** Enforces policy for passphrase generation options.
 */
class bw_PassphraseGeneratorOptionsEvaluator {
    /** Instantiates the evaluator.
     * @param policy The policy applied by the evaluator. When this conflicts with
     *               the defaults, the policy takes precedence.
     */
    constructor(policy) {
        function createBoundary(value, defaultBoundary) {
            const boundary = {
                min: Math.max(defaultBoundary.min, value),
                max: Math.max(defaultBoundary.max, value),
            };
            return boundary;
        }
        this.policy = structuredClone(policy);
        this.numWords = createBoundary(policy.minNumberWords, bw_DefaultPassphraseBoundaries.numWords);
    }
    /** {@link PolicyEvaluator.policyInEffect} */
    get policyInEffect() {
        const policies = [
            this.policy.capitalize,
            this.policy.includeNumber,
            this.policy.minNumberWords > bw_DefaultPassphraseBoundaries.numWords.min,
        ];
        return policies.includes(true);
    }
    /** Apply policy to the input options.
     *  @param options The options to build from. These options are not altered.
     *  @returns A new password generation request with policy applied.
     */
    applyPolicy(options) {
        function fitToBounds(value, boundaries) {
            const { min, max } = boundaries;
            const withUpperBound = Math.min(value !== null && value !== void 0 ? value : boundaries.min, max);
            const withLowerBound = Math.max(withUpperBound, min);
            return withLowerBound;
        }
        // apply policy overrides
        const capitalize = this.policy.capitalize || options.capitalize || false;
        const includeNumber = this.policy.includeNumber || options.includeNumber || false;
        // apply boundaries
        const numWords = fitToBounds(options.numWords, this.numWords);
        return Object.assign(Object.assign({}, options), { numWords,
            capitalize,
            includeNumber });
    }
    /** Ensures internal options consistency.
     *  @param options The options to cascade. These options are not altered.
     *  @returns A passphrase generation request with cascade applied.
     */
    sanitize(options) {
        var _a, _b;
        // ensure words are separated by a single character or the empty string
        const wordSeparator = options.wordSeparator === ""
            ? ""
            : ((_b = (_a = options.wordSeparator) === null || _a === void 0 ? void 0 : _a[0]) !== null && _b !== void 0 ? _b : bw_DefaultPassphraseGenerationOptions.wordSeparator);
        return Object.assign(Object.assign({}, options), { wordSeparator });
    }
}

;// ../../libs/tools/generator/core/src/policies/passphrase-policy-constraints.ts


class bw_PassphrasePolicyConstraints {
    /** Creates a passphrase policy constraints
     *  @param policy the password policy to enforce. This cannot be
     *  `null` or `undefined`.
     */
    constructor(policy, defaults) {
        this.policy = policy;
        this.defaults = defaults;
        this.constraints = {
            policyInEffect: bw_passphrase_policy_constraints_policyInEffect(policy, defaults),
            wordSeparator: { minLength: 0, maxLength: 1 },
            capitalize: bw_readonlyTrueWhen(policy.capitalize),
            includeNumber: bw_readonlyTrueWhen(policy.includeNumber),
            numWords: bw_atLeast(policy.minNumberWords, defaults.numWords),
        };
    }
    adjust(state) {
        const result = {
            wordSeparator: bw_fitLength(state.wordSeparator, this.constraints.wordSeparator, {
                fillString: bw_DefaultPassphraseGenerationOptions.wordSeparator,
            }),
            capitalize: bw_enforceConstant(state.capitalize, this.constraints.capitalize),
            includeNumber: bw_enforceConstant(state.includeNumber, this.constraints.includeNumber),
            numWords: bw_fitToBounds(state.numWords, this.constraints.numWords),
        };
        return result;
    }
    fix(state) {
        return state;
    }
}
function bw_passphrase_policy_constraints_policyInEffect(policy, defaults) {
    const policies = [
        policy.capitalize,
        policy.includeNumber,
        policy.minNumberWords > defaults.numWords.min,
    ];
    return policies.includes(true);
}

;// ../../libs/tools/generator/core/src/policies/password-generator-options-evaluator.ts

/** Enforces policy for password generation.
 */
class bw_PasswordGeneratorOptionsEvaluator {
    // Constraints<PasswordGenerationOptions> compatibility
    get minNumber() {
        return this.minDigits;
    }
    get minSpecial() {
        return this.minSpecialCharacters;
    }
    /** Instantiates the evaluator.
     * @param policy The policy applied by the evaluator. When this conflicts with
     *               the defaults, the policy takes precedence.
     */
    constructor(policy) {
        function createBoundary(value, defaultBoundary) {
            const boundary = {
                min: Math.max(defaultBoundary.min, value),
                max: Math.max(defaultBoundary.max, value),
            };
            return boundary;
        }
        this.policy = structuredClone(policy);
        this.minDigits = createBoundary(policy.numberCount, bw_DefaultPasswordBoundaries.minDigits);
        this.minSpecialCharacters = createBoundary(policy.specialCount, bw_DefaultPasswordBoundaries.minSpecialCharacters);
        // the overall length should be at least as long as the sum of the minimums
        const minConsistentLength = this.minDigits.min + this.minSpecialCharacters.min;
        const minPolicyLength = policy.minLength > 0 ? policy.minLength : bw_DefaultPasswordBoundaries.length.min;
        const minLength = Math.max(minPolicyLength, minConsistentLength, bw_DefaultPasswordBoundaries.length.min);
        this.length = {
            min: minLength,
            max: Math.max(bw_DefaultPasswordBoundaries.length.max, minLength),
        };
    }
    /** {@link PolicyEvaluator.policyInEffect} */
    get policyInEffect() {
        const policies = [
            this.policy.useUppercase,
            this.policy.useLowercase,
            this.policy.useNumbers,
            this.policy.useSpecial,
            this.policy.minLength > bw_DefaultPasswordBoundaries.length.min,
            this.policy.numberCount > bw_DefaultPasswordBoundaries.minDigits.min,
            this.policy.specialCount > bw_DefaultPasswordBoundaries.minSpecialCharacters.min,
        ];
        return policies.includes(true);
    }
    /** {@link PolicyEvaluator.applyPolicy} */
    applyPolicy(options) {
        function fitToBounds(value, boundaries) {
            const { min, max } = boundaries;
            const withUpperBound = Math.min(value || 0, max);
            const withLowerBound = Math.max(withUpperBound, min);
            return withLowerBound;
        }
        // apply policy overrides
        const uppercase = this.policy.useUppercase || options.uppercase || false;
        const lowercase = this.policy.useLowercase || options.lowercase || false;
        // these overrides can cascade numeric fields to boolean fields
        const number = this.policy.useNumbers || options.number || options.minNumber > 0;
        const special = this.policy.useSpecial || options.special || options.minSpecial > 0;
        // apply boundaries; the boundaries can cascade boolean fields to numeric fields
        const length = fitToBounds(options.length, this.length);
        const minNumber = fitToBounds(options.minNumber, this.minDigits);
        const minSpecial = fitToBounds(options.minSpecial, this.minSpecialCharacters);
        return Object.assign(Object.assign({}, options), { length,
            uppercase,
            lowercase,
            number,
            minNumber,
            special,
            minSpecial });
    }
    /** {@link PolicyEvaluator.sanitize} */
    sanitize(options) {
        var _a;
        function cascade(enabled, value) {
            const enabledResult = enabled !== null && enabled !== void 0 ? enabled : value > 0;
            const valueResult = enabledResult ? value || 1 : 0;
            return [enabledResult, valueResult];
        }
        const [lowercase, minLowercase] = cascade(options.lowercase, options.minLowercase);
        const [uppercase, minUppercase] = cascade(options.uppercase, options.minUppercase);
        const [number, minNumber] = cascade(options.number, options.minNumber);
        const [special, minSpecial] = cascade(options.special, options.minSpecial);
        // minimums can only increase the length
        const minConsistentLength = minLowercase + minUppercase + minNumber + minSpecial;
        const minLength = Math.max(minConsistentLength, this.length.min);
        const length = Math.max((_a = options.length) !== null && _a !== void 0 ? _a : minLength, minLength);
        return Object.assign(Object.assign({}, options), { length,
            minLength,
            lowercase,
            minLowercase,
            uppercase,
            minUppercase,
            number,
            minNumber,
            special,
            minSpecial });
    }
}

;// ../../libs/tools/generator/core/src/policies/passphrase-least-privilege.ts

/** Reduces a policy into an accumulator by accepting the most restrictive
 *  values from each policy.
 *  @param acc the accumulator
 *  @param policy the policy to reduce
 *  @returns the most restrictive values between the policy and accumulator.
 */
function bw_passphraseLeastPrivilege(acc, policy) {
    var _a;
    if (policy.type !== bw_policy_type_enum_PolicyType.PasswordGenerator) {
        return acc;
    }
    return {
        minNumberWords: Math.max(acc.minNumberWords, (_a = policy.data.minNumberWords) !== null && _a !== void 0 ? _a : acc.minNumberWords),
        capitalize: policy.data.capitalize || acc.capitalize,
        includeNumber: policy.data.includeNumber || acc.includeNumber,
    };
}

;// ../../libs/tools/generator/core/src/policies/password-least-privilege.ts

/** Reduces a policy into an accumulator by accepting the most restrictive
 *  values from each policy.
 *  @param acc the accumulator
 *  @param policy the policy to reduce
 *  @returns the most restrictive values between the policy and accumulator.
 */
function bw_passwordLeastPrivilege(acc, policy) {
    var _a, _b, _c;
    if (policy.type !== bw_policy_type_enum_PolicyType.PasswordGenerator || !policy.enabled) {
        return acc;
    }
    return {
        minLength: Math.max(acc.minLength, (_a = policy.data.minLength) !== null && _a !== void 0 ? _a : acc.minLength),
        useUppercase: policy.data.useUpper || acc.useUppercase,
        useLowercase: policy.data.useLower || acc.useLowercase,
        useNumbers: policy.data.useNumbers || acc.useNumbers,
        numberCount: Math.max(acc.numberCount, (_b = policy.data.minNumbers) !== null && _b !== void 0 ? _b : acc.numberCount),
        useSpecial: policy.data.useSpecial || acc.useSpecial,
        specialCount: Math.max(acc.specialCount, (_c = policy.data.minSpecial) !== null && _c !== void 0 ? _c : acc.specialCount),
    };
}

;// ../../libs/tools/generator/core/src/policies/index.ts








;// ../../libs/tools/generator/core/src/policies/catchall-constraints.ts
/** Parses the domain part of an email address
 */
const bw_DOMAIN_PARSER = new RegExp("[^@]+@(?<domain>.+)");
/** A constraint that sets the catchall domain using a fixed email address */
class bw_CatchallConstraints {
    /** Creates a catchall constraints
     * @param email - the email address containing the domain.
     */
    constructor(email) {
        var _a;
        this.constraints = {};
        if (!email) {
            this.domain = "";
            return;
        }
        const parsed = bw_DOMAIN_PARSER.exec(email);
        if (parsed && ((_a = parsed.groups) === null || _a === void 0 ? void 0 : _a.domain)) {
            this.domain = parsed.groups.domain;
        }
    }
    adjust(state) {
        var _a;
        const currentDomain = ((_a = state.catchallDomain) !== null && _a !== void 0 ? _a : "").trim();
        if (currentDomain !== "") {
            return state;
        }
        const options = Object.assign({}, state);
        options.catchallDomain = this.domain;
        return options;
    }
    fix(state) {
        return state;
    }
}

;// ../../libs/tools/generator/core/src/policies/subaddress-constraints.ts
/** A constraint that sets the subaddress email using a fixed email address */
class bw_SubaddressConstraints {
    /** Creates a catchall constraints
     * @param email - the email address containing the domain.
     */
    constructor(email) {
        this.email = email;
        this.constraints = {};
        if (!email) {
            this.email = "";
        }
    }
    adjust(state) {
        var _a;
        const currentDomain = ((_a = state.subaddressEmail) !== null && _a !== void 0 ? _a : "").trim();
        if (currentDomain !== "") {
            return state;
        }
        const options = Object.assign({}, state);
        options.subaddressEmail = this.email;
        return options;
    }
    fix(state) {
        return state;
    }
}

;// ../../libs/tools/generator/core/src/data/default-catchall-options.ts
/** The default options for catchall address generation. */
const bw_DefaultCatchallOptions = Object.freeze({
    catchallType: "random",
    catchallDomain: "",
    website: null,
});

;// ../../libs/tools/generator/core/src/data/default-eff-username-options.ts
/** The default options for EFF long word generation. */
const bw_DefaultEffUsernameOptions = Object.freeze({
    wordCapitalize: false,
    wordIncludeNumber: false,
    website: null,
});

;// ../../libs/tools/generator/core/src/data/default-passphrase-boundaries.ts
function bw_initializeBoundaries() {
    const numWords = Object.freeze({
        min: 3,
        max: 20,
    });
    return Object.freeze({
        numWords,
    });
}
/** Immutable default boundaries for passphrase generation.
 * These are used when the policy does not override a value.
 */
const bw_DefaultPassphraseBoundaries = bw_initializeBoundaries();

;// ../../libs/tools/generator/core/src/data/default-passphrase-generation-options.ts
/** The default options for passphrase generation. */
const bw_DefaultPassphraseGenerationOptions = Object.freeze({
    numWords: 6,
    wordSeparator: "-",
    capitalize: false,
    includeNumber: false,
});

;// ../../libs/tools/generator/core/src/data/default-password-boundaries.ts
function bw_default_password_boundaries_initializeBoundaries() {
    const length = Object.freeze({
        min: 5,
        max: 128,
    });
    const minDigits = Object.freeze({
        min: 0,
        max: 9,
    });
    const minSpecialCharacters = Object.freeze({
        min: 0,
        max: 9,
    });
    return Object.freeze({
        length,
        minDigits,
        minSpecialCharacters,
    });
}
/** Immutable default boundaries for password generation.
 * These are used when the policy does not override a value.
 */
const bw_DefaultPasswordBoundaries = bw_default_password_boundaries_initializeBoundaries();

;// ../../libs/tools/generator/core/src/data/default-password-generation-options.ts

/** The default options for password generation. */
const bw_DefaultPasswordGenerationOptions = Object.freeze({
    length: 14,
    minLength: bw_DefaultPasswordBoundaries.length.min,
    ambiguous: true,
    uppercase: true,
    minUppercase: 1,
    lowercase: true,
    minLowercase: 1,
    number: true,
    minNumber: 1,
    special: false,
    minSpecial: 0,
});

;// ../../libs/tools/generator/core/src/data/default-subaddress-generator-options.ts
/** The default options for email subaddress generation. */
const bw_DefaultSubaddressOptions = Object.freeze({
    subaddressType: "random",
    subaddressEmail: "",
    website: null,
});

;// ../../libs/tools/generator/core/src/data/generators.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
















const bw_PASSPHRASE = Object.freeze({
    id: "passphrase",
    category: "password",
    nameKey: "passphrase",
    generateKey: "generatePassphrase",
    onGeneratedMessageKey: "passphraseGenerated",
    credentialTypeKey: "passphrase",
    copyKey: "copyPassphrase",
    useGeneratedValueKey: "useThisPassword",
    onlyOnRequest: false,
    request: [],
    engine: {
        create(dependencies) {
            return new bw_PasswordRandomizer(dependencies.randomizer);
        },
    },
    settings: {
        initial: bw_DefaultPassphraseGenerationOptions,
        constraints: {
            numWords: {
                min: bw_DefaultPassphraseBoundaries.numWords.min,
                max: bw_DefaultPassphraseBoundaries.numWords.max,
                recommendation: bw_DefaultPassphraseGenerationOptions.numWords,
            },
            wordSeparator: { maxLength: 1 },
        },
        account: {
            key: "passphraseGeneratorSettings",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier([
                "numWords",
                "wordSeparator",
                "capitalize",
                "includeNumber",
            ]),
            state: bw_GENERATOR_DISK,
            initial: bw_DefaultPassphraseGenerationOptions,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
    },
    policy: {
        type: bw_policy_type_enum_PolicyType.PasswordGenerator,
        disabledValue: Object.freeze({
            minNumberWords: 0,
            capitalize: false,
            includeNumber: false,
        }),
        combine: bw_passphraseLeastPrivilege,
        createEvaluator: (policy) => new bw_PassphraseGeneratorOptionsEvaluator(policy),
        toConstraints: (policy) => new bw_PassphrasePolicyConstraints(policy, bw_PASSPHRASE.settings.constraints),
    },
});
const bw_PASSWORD = Object.freeze({
    id: "password",
    category: "password",
    nameKey: "password",
    generateKey: "generatePassword",
    onGeneratedMessageKey: "passwordGenerated",
    credentialTypeKey: "password",
    copyKey: "copyPassword",
    useGeneratedValueKey: "useThisPassword",
    onlyOnRequest: false,
    request: [],
    engine: {
        create(dependencies) {
            return new bw_PasswordRandomizer(dependencies.randomizer);
        },
    },
    settings: {
        initial: bw_DefaultPasswordGenerationOptions,
        constraints: {
            length: {
                min: bw_DefaultPasswordBoundaries.length.min,
                max: bw_DefaultPasswordBoundaries.length.max,
                recommendation: bw_DefaultPasswordGenerationOptions.length,
            },
            minNumber: {
                min: bw_DefaultPasswordBoundaries.minDigits.min,
                max: bw_DefaultPasswordBoundaries.minDigits.max,
            },
            minSpecial: {
                min: bw_DefaultPasswordBoundaries.minSpecialCharacters.min,
                max: bw_DefaultPasswordBoundaries.minSpecialCharacters.max,
            },
        },
        account: {
            key: "passwordGeneratorSettings",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier([
                "length",
                "ambiguous",
                "uppercase",
                "minUppercase",
                "lowercase",
                "minLowercase",
                "number",
                "minNumber",
                "special",
                "minSpecial",
            ]),
            state: bw_GENERATOR_DISK,
            initial: bw_DefaultPasswordGenerationOptions,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
    },
    policy: {
        type: bw_policy_type_enum_PolicyType.PasswordGenerator,
        disabledValue: Object.freeze({
            minLength: 0,
            useUppercase: false,
            useLowercase: false,
            useNumbers: false,
            numberCount: 0,
            useSpecial: false,
            specialCount: 0,
        }),
        combine: bw_passwordLeastPrivilege,
        createEvaluator: (policy) => new bw_PasswordGeneratorOptionsEvaluator(policy),
        toConstraints: (policy) => new bw_DynamicPasswordPolicyConstraints(policy, bw_PASSWORD.settings.constraints),
    },
});
const bw_USERNAME = Object.freeze({
    id: "username",
    category: "username",
    nameKey: "randomWord",
    generateKey: "generateUsername",
    onGeneratedMessageKey: "usernameGenerated",
    credentialTypeKey: "username",
    copyKey: "copyUsername",
    useGeneratedValueKey: "useThisUsername",
    onlyOnRequest: false,
    request: [],
    engine: {
        create(dependencies) {
            return new bw_UsernameRandomizer(dependencies.randomizer);
        },
    },
    settings: {
        initial: bw_DefaultEffUsernameOptions,
        constraints: {},
        account: {
            key: "effUsernameGeneratorSettings",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier([
                "wordCapitalize",
                "wordIncludeNumber",
            ]),
            state: bw_GENERATOR_DISK,
            initial: bw_DefaultEffUsernameOptions,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
    },
    policy: {
        type: bw_policy_type_enum_PolicyType.PasswordGenerator,
        disabledValue: {},
        combine(_acc, _policy) {
            return {};
        },
        createEvaluator(_policy) {
            return new bw_default_policy_evaluator_DefaultPolicyEvaluator();
        },
        toConstraints(_policy) {
            return new bw_identity_state_constraint_IdentityConstraint();
        },
    },
});
const bw_CATCHALL = Object.freeze({
    id: "catchall",
    category: "email",
    nameKey: "catchallEmail",
    descriptionKey: "catchallEmailDesc",
    generateKey: "generateEmail",
    onGeneratedMessageKey: "emailGenerated",
    credentialTypeKey: "email",
    copyKey: "copyEmail",
    useGeneratedValueKey: "useThisEmail",
    onlyOnRequest: false,
    request: [],
    engine: {
        create(dependencies) {
            return new bw_EmailRandomizer(dependencies.randomizer);
        },
    },
    settings: {
        initial: bw_DefaultCatchallOptions,
        constraints: { catchallDomain: { minLength: 1 } },
        account: {
            key: "catchallGeneratorSettings",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier([
                "catchallType",
                "catchallDomain",
            ]),
            state: bw_GENERATOR_DISK,
            initial: {
                catchallType: "random",
                catchallDomain: "",
            },
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
    },
    policy: {
        type: bw_policy_type_enum_PolicyType.PasswordGenerator,
        disabledValue: {},
        combine(_acc, _policy) {
            return {};
        },
        createEvaluator(_policy) {
            return new bw_default_policy_evaluator_DefaultPolicyEvaluator();
        },
        toConstraints(_policy, email) {
            return new bw_CatchallConstraints(email);
        },
    },
});
const bw_SUBADDRESS = Object.freeze({
    id: "subaddress",
    category: "email",
    nameKey: "plusAddressedEmail",
    descriptionKey: "plusAddressedEmailDesc",
    generateKey: "generateEmail",
    onGeneratedMessageKey: "emailGenerated",
    credentialTypeKey: "email",
    copyKey: "copyEmail",
    useGeneratedValueKey: "useThisEmail",
    onlyOnRequest: false,
    request: [],
    engine: {
        create(dependencies) {
            return new bw_EmailRandomizer(dependencies.randomizer);
        },
    },
    settings: {
        initial: bw_DefaultSubaddressOptions,
        constraints: {},
        account: {
            key: "subaddressGeneratorSettings",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier([
                "subaddressType",
                "subaddressEmail",
            ]),
            state: bw_GENERATOR_DISK,
            initial: {
                subaddressType: "random",
                subaddressEmail: "",
            },
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
    },
    policy: {
        type: bw_policy_type_enum_PolicyType.PasswordGenerator,
        disabledValue: {},
        combine(_acc, _policy) {
            return {};
        },
        createEvaluator(_policy) {
            return new bw_default_policy_evaluator_DefaultPolicyEvaluator();
        },
        toConstraints(_policy, email) {
            return new bw_SubaddressConstraints(email);
        },
    },
});
function bw_generators_toCredentialGeneratorConfiguration(configuration) {
    const forwarder = Object.freeze({
        id: { forwarder: configuration.id },
        category: "email",
        nameKey: configuration.name,
        descriptionKey: "forwardedEmailDesc",
        generateKey: "generateEmail",
        onGeneratedMessageKey: "emailGenerated",
        credentialTypeKey: "email",
        copyKey: "copyEmail",
        useGeneratedValueKey: "useThisEmail",
        onlyOnRequest: true,
        request: configuration.forwarder.request,
        engine: {
            create(dependencies) {
                // FIXME: figure out why `configuration` fails to typecheck
                const config = configuration;
                return new Forwarder(config, dependencies.client, dependencies.i18nService);
            },
        },
        settings: {
            initial: configuration.forwarder.defaultSettings,
            constraints: configuration.forwarder.settingsConstraints,
            account: configuration.forwarder.local.settings,
        },
        policy: {
            type: PolicyType.PasswordGenerator,
            disabledValue: {},
            combine(_acc, _policy) {
                return {};
            },
            createEvaluator(_policy) {
                return new DefaultPolicyEvaluator();
            },
            toConstraints(_policy) {
                return new IdentityConstraint();
            },
        },
    });
    return forwarder;
}
/** Generator configurations */
const bw_generators_Generators = Object.freeze({
    /** Passphrase generator configuration */
    passphrase: bw_PASSPHRASE,
    /** Password generator configuration */
    password: bw_PASSWORD,
    /** Username generator configuration */
    username: bw_USERNAME,
    /** Catchall email generator configuration */
    catchall: bw_CATCHALL,
    /** Email subaddress generator configuration */
    subaddress: bw_SUBADDRESS,
});

;// ../../libs/tools/generator/core/src/data/default-addy-io-options.ts
const bw_DefaultAddyIoOptions = Object.freeze({
    website: null,
    baseUrl: "https://app.addy.io",
    token: "",
    domain: "",
});

;// ../../libs/tools/generator/core/src/data/default-duck-duck-go-options.ts
const bw_DefaultDuckDuckGoOptions = Object.freeze({
    website: null,
    token: "",
});

;// ../../libs/tools/generator/core/src/data/default-fastmail-options.ts
const bw_DefaultFastmailOptions = Object.freeze({
    website: "",
    domain: "",
    prefix: "",
    token: "",
});

;// ../../libs/tools/generator/core/src/data/default-forward-email-options.ts
const bw_DefaultForwardEmailOptions = Object.freeze({
    website: null,
    token: "",
    domain: "",
});

;// ../../libs/tools/generator/core/src/data/default-firefox-relay-options.ts
const bw_DefaultFirefoxRelayOptions = Object.freeze({
    website: null,
    token: "",
});

;// ../../libs/tools/generator/core/src/data/default-credential-preferences.ts

const bw_DefaultCredentialPreferences = Object.freeze({
    email: Object.freeze({
        algorithm: bw_generator_types_EmailAlgorithms[0],
        updated: new Date(0),
    }),
    password: Object.freeze({
        algorithm: bw_generator_types_PasswordAlgorithms[0],
        updated: new Date(0),
    }),
    username: Object.freeze({
        algorithm: bw_generator_types_UsernameAlgorithms[0],
        updated: new Date(0),
    }),
});

;// ../../libs/tools/generator/core/src/data/default-simple-login-options.ts
const bw_DefaultSimpleLoginOptions = Object.freeze({
    website: null,
    baseUrl: "https://app.simplelogin.io",
    token: "",
});

;// ../../libs/tools/generator/core/src/data/forwarders.ts
/** Metadata about an email forwarding service.
 *  @remarks This is used to populate the forwarder selection list
 *  and to identify forwarding services in error messages.
 */
const bw_forwarders_Forwarders = Object.freeze({
    /** For https://addy.io/ */
    AddyIo: Object.freeze({
        id: "anonaddy",
        name: "Addy.io",
        validForSelfHosted: true,
    }),
    /** For https://duckduckgo.com/email/ */
    DuckDuckGo: Object.freeze({
        id: "duckduckgo",
        name: "DuckDuckGo",
        validForSelfHosted: false,
    }),
    /** For https://www.fastmail.com. */
    Fastmail: Object.freeze({
        id: "fastmail",
        name: "Fastmail",
        validForSelfHosted: true,
    }),
    /** For https://relay.firefox.com/ */
    FirefoxRelay: Object.freeze({
        id: "firefoxrelay",
        name: "Firefox Relay",
        validForSelfHosted: false,
    }),
    /** For https://forwardemail.net/ */
    ForwardEmail: Object.freeze({
        id: "forwardemail",
        name: "Forward Email",
        validForSelfHosted: true,
    }),
    /** For https://simplelogin.io/ */
    SimpleLogin: Object.freeze({
        id: "simplelogin",
        name: "SimpleLogin",
        validForSelfHosted: true,
    }),
});

;// ../../libs/common/src/tools/private-classifier.ts
class bw_PrivateClassifier {
    constructor(keys = undefined) {
        this.keys = keys;
    }
    classify(value) {
        var _a;
        const pickMe = JSON.parse(JSON.stringify(value));
        const keys = (_a = this.keys) !== null && _a !== void 0 ? _a : Object.keys(pickMe);
        const picked = {};
        for (const key of keys) {
            picked[key] = pickMe[key];
        }
        const secret = picked;
        return { disclosed: {}, secret };
    }
    declassify(_disclosed, secret) {
        var _a;
        const result = {};
        const keys = (_a = this.keys) !== null && _a !== void 0 ? _a : Object.keys(secret);
        for (const key of keys) {
            result[key] = secret[key];
        }
        return result;
    }
}

;// ../../libs/common/src/tools/state/buffered-key-definition.ts

/** Storage and mapping settings for data stored by a `BufferedState`.
 */
class bw_BufferedKeyDefinition {
    /**
     * Defines a buffered state
     * @param stateDefinition The domain of the buffer
     * @param key Domain key that identifies the buffered value. This key must
     *    not be reused in any capacity.
     * @param options Configures the operation of the buffered state.
     */
    constructor(stateDefinition, key, options) {
        this.stateDefinition = stateDefinition;
        this.key = key;
        this.options = options;
    }
    /** Converts the buffered key definition to a state provider
     *  key definition
     */
    toKeyDefinition() {
        const bufferedKey = new bw_UserKeyDefinition(this.stateDefinition, this.key, this.options);
        return bufferedKey;
    }
    /** Checks whether the dependency triggers an overwrite. */
    shouldOverwrite(dependency) {
        var _a;
        const shouldOverwrite = (_a = this.options) === null || _a === void 0 ? void 0 : _a.shouldOverwrite;
        if (shouldOverwrite) {
            return shouldOverwrite(dependency);
        }
        return dependency ? true : false;
    }
    /** Converts the input data format to its output format.
     *  @returns the converted value.
     */
    map(input, dependency) {
        var _a;
        const map = (_a = this.options) === null || _a === void 0 ? void 0 : _a.map;
        if (map) {
            return map(input, dependency);
        }
        return Promise.resolve(input);
    }
    /** Checks whether the input type can be converted to the output type.
     *  @returns `true` if the definition is defined and valid, otherwise `false`.
     */
    isValid(input, dependency) {
        var _a;
        if (input === null) {
            return Promise.resolve(false);
        }
        const isValid = (_a = this.options) === null || _a === void 0 ? void 0 : _a.isValid;
        if (isValid) {
            return isValid(input, dependency);
        }
        return Promise.resolve(input ? true : false);
    }
}

;// ../../libs/tools/generator/core/src/integration/addy-io.ts




// default values
const bw_defaultSettings = Object.freeze({
    token: "",
    domain: "",
    baseUrl: "",
});
// supported RPC calls
const bw_createForwardingEmail = Object.freeze({
    url(_request, context) {
        return context.baseUrl() + "/api/v1/aliases";
    },
    body(request, context) {
        return {
            domain: context.emailDomain(),
            description: context.generatedBy(request),
        };
    },
    hasJsonPayload(response) {
        return response.status === 200 || response.status === 201;
    },
    processJson(json) {
        var _a;
        return [(_a = json === null || json === void 0 ? void 0 : json.data) === null || _a === void 0 ? void 0 : _a.email];
    },
});
// forwarder configuration
const bw_forwarder = Object.freeze({
    defaultSettings: bw_defaultSettings,
    createForwardingEmail: bw_createForwardingEmail,
    request: ["token", "baseUrl", "domain"],
    settingsConstraints: {
        token: { required: true },
        domain: { required: true },
        baseUrl: {},
    },
    local: {
        settings: {
            // FIXME: integration should issue keys at runtime
            // based on integrationId & extension metadata
            // e.g. key: "forwarder.AddyIo.local.settings",
            key: "addyIoForwarder",
            target: "object",
            format: "secret-state",
            frame: 512,
            classifier: new bw_PrivateClassifier(),
            state: bw_GENERATOR_DISK,
            initial: bw_defaultSettings,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
        import: {
            key: "forwarder.AddyIo.local.import",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier(["token", "baseUrl", "domain"]),
            state: bw_GENERATOR_MEMORY,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout", "lock"],
            },
        },
    },
    settings: new bw_UserKeyDefinition(bw_GENERATOR_DISK, "addyIoForwarder", {
        deserializer: (value) => value,
        clearOn: [],
    }),
    importBuffer: new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "addyIoBuffer", {
        deserializer: (value) => value,
        clearOn: ["logout"],
    }),
});
const bw_AddyIo = Object.freeze({
    // integration
    id: "anonaddy",
    name: "Addy.io",
    extends: ["forwarder"],
    // hosting
    selfHost: "maybe",
    baseUrl: "https://app.addy.io",
    authenticate(_request, context) {
        return { Authorization: "Bearer " + context.authenticationToken() };
    },
    // extensions
    forwarder: bw_forwarder,
});

;// ../../libs/tools/generator/core/src/integration/duck-duck-go.ts




// default values
const bw_duck_duck_go_defaultSettings = Object.freeze({
    token: "",
});
// supported RPC calls
const bw_duck_duck_go_createForwardingEmail = Object.freeze({
    url(_request, context) {
        return context.baseUrl() + "/email/addresses";
    },
    body(_request, _context) {
        return undefined;
    },
    hasJsonPayload(response) {
        return response.status === 200 || response.status === 201;
    },
    processJson(json) {
        return [`${json.address}@duck.com`];
    },
});
// forwarder configuration
const bw_duck_duck_go_forwarder = Object.freeze({
    defaultSettings: bw_duck_duck_go_defaultSettings,
    createForwardingEmail: bw_duck_duck_go_createForwardingEmail,
    request: ["token"],
    settingsConstraints: {
        token: { required: true },
    },
    local: {
        settings: {
            // FIXME: integration should issue keys at runtime
            // based on integrationId & extension metadata
            // e.g. key: "forwarder.DuckDuckGo.local.settings",
            key: "duckDuckGoForwarder",
            target: "object",
            format: "secret-state",
            frame: 512,
            classifier: new bw_PrivateClassifier(),
            state: bw_GENERATOR_DISK,
            initial: bw_duck_duck_go_defaultSettings,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
        import: {
            key: "forwarder.DuckDuckGo.local.import",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier(["token"]),
            state: bw_GENERATOR_MEMORY,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout", "lock"],
            },
        },
    },
    settings: new bw_UserKeyDefinition(bw_GENERATOR_DISK, "duckDuckGoForwarder", {
        deserializer: (value) => value,
        clearOn: [],
    }),
    importBuffer: new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "duckDuckGoBuffer", {
        deserializer: (value) => value,
        clearOn: ["logout"],
    }),
});
// integration-wide configuration
const bw_DuckDuckGo = Object.freeze({
    id: "duckduckgo",
    name: "DuckDuckGo",
    baseUrl: "https://quack.duckduckgo.com/api",
    selfHost: "never",
    extends: ["forwarder"],
    authenticate(_request, context) {
        return { Authorization: "Bearer " + context.authenticationToken() };
    },
    forwarder: bw_duck_duck_go_forwarder,
});

;// ../../libs/tools/generator/core/src/integration/fastmail.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




// default values
const bw_fastmail_defaultSettings = Object.freeze({
    domain: "",
    prefix: "",
    token: "",
});
// supported RPC calls
const bw_getAccountId = Object.freeze({
    url(_request, context) {
        // cannot use "/.well-known/jmap" because integration RPCs
        // never follow redirects
        return context.baseUrl() + "/jmap/session";
    },
    hasJsonPayload(response) {
        return response.status === 200;
    },
    processJson(json, context) {
        var _a, _b;
        const result = (_b = (_a = json.primaryAccounts) === null || _a === void 0 ? void 0 : _a["https://www.fastmail.com/dev/maskedemail"]) !== null && _b !== void 0 ? _b : undefined;
        return [result, result ? undefined : context.missingAccountIdCause()];
    },
});
const bw_fastmail_createForwardingEmail = Object.freeze({
    url(_request, context) {
        return context.baseUrl() + "/jmap/api/";
    },
    body(request, context) {
        const body = {
            using: ["https://www.fastmail.com/dev/maskedemail", "urn:ietf:params:jmap:core"],
            methodCalls: [
                [
                    "MaskedEmail/set",
                    {
                        accountId: request.accountId,
                        create: {
                            "new-masked-email": {
                                state: "enabled",
                                description: "",
                                forDomain: context.website(request),
                                emailPrefix: "",
                            },
                        },
                    },
                    "0",
                ],
            ],
        };
        return body;
    },
    hasJsonPayload(response) {
        return response.status === 200;
    },
    processJson(json) {
        var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l;
        if (json.methodResponses != null &&
            json.methodResponses.length > 0 &&
            json.methodResponses[0].length > 0) {
            if (json.methodResponses[0][0] === "MaskedEmail/set") {
                if (((_b = (_a = json.methodResponses[0][1]) === null || _a === void 0 ? void 0 : _a.created) === null || _b === void 0 ? void 0 : _b["new-masked-email"]) != null) {
                    const email = (_e = (_d = (_c = json.methodResponses[0][1]) === null || _c === void 0 ? void 0 : _c.created) === null || _d === void 0 ? void 0 : _d["new-masked-email"]) === null || _e === void 0 ? void 0 : _e.email;
                    return [email];
                }
                if (((_g = (_f = json.methodResponses[0][1]) === null || _f === void 0 ? void 0 : _f.notCreated) === null || _g === void 0 ? void 0 : _g["new-masked-email"]) != null) {
                    const errorDescription = (_k = (_j = (_h = json.methodResponses[0][1]) === null || _h === void 0 ? void 0 : _h.notCreated) === null || _j === void 0 ? void 0 : _j["new-masked-email"]) === null || _k === void 0 ? void 0 : _k.description;
                    return [undefined, errorDescription];
                }
            }
            else if (json.methodResponses[0][0] === "error") {
                const errorDescription = (_l = json.methodResponses[0][1]) === null || _l === void 0 ? void 0 : _l.description;
                return [undefined, errorDescription];
            }
        }
    },
});
// forwarder configuration
const bw_fastmail_forwarder = Object.freeze({
    defaultSettings: bw_fastmail_defaultSettings,
    createForwardingEmail: bw_fastmail_createForwardingEmail,
    getAccountId: bw_getAccountId,
    request: ["token"],
    settingsConstraints: {
        token: { required: true },
        domain: { required: true },
        prefix: {},
    },
    local: {
        settings: {
            // FIXME: integration should issue keys at runtime
            // based on integrationId & extension metadata
            // e.g. key: "forwarder.Fastmail.local.settings"
            key: "fastmailForwarder",
            target: "object",
            format: "secret-state",
            frame: 512,
            classifier: new bw_PrivateClassifier(),
            state: bw_GENERATOR_DISK,
            initial: bw_fastmail_defaultSettings,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
        import: {
            key: "forwarder.Fastmail.local.import",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier(["token"]),
            state: bw_GENERATOR_MEMORY,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout", "lock"],
            },
        },
    },
    settings: new bw_UserKeyDefinition(bw_GENERATOR_DISK, "fastmailForwarder", {
        deserializer: (value) => value,
        clearOn: [],
    }),
    importBuffer: new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "fastmailBuffer", {
        deserializer: (value) => value,
        clearOn: ["logout"],
    }),
});
// integration-wide configuration
const bw_Fastmail = Object.freeze({
    id: "fastmail",
    name: "Fastmail",
    baseUrl: "https://api.fastmail.com",
    selfHost: "maybe",
    extends: ["forwarder"],
    authenticate(_request, context) {
        return { Authorization: "Bearer " + context.authenticationToken() };
    },
    forwarder: bw_fastmail_forwarder,
});

;// ../../libs/tools/generator/core/src/integration/firefox-relay.ts




// default values
const bw_firefox_relay_defaultSettings = Object.freeze({
    token: "",
});
// supported RPC calls
const bw_firefox_relay_createForwardingEmail = Object.freeze({
    url(_request, context) {
        return context.baseUrl() + "/v1/relayaddresses/";
    },
    body(request, context) {
        return {
            enabled: true,
            generated_for: context.website(request),
            description: context.generatedBy(request),
        };
    },
    hasJsonPayload(response) {
        return response.status === 200 || response.status === 201;
    },
    processJson(json) {
        return [json.full_address];
    },
});
// forwarder configuration
const bw_firefox_relay_forwarder = Object.freeze({
    defaultSettings: bw_firefox_relay_defaultSettings,
    createForwardingEmail: bw_firefox_relay_createForwardingEmail,
    request: ["token"],
    settingsConstraints: {
        token: { required: true },
    },
    local: {
        settings: {
            // FIXME: integration should issue keys at runtime
            // based on integrationId & extension metadata
            // e.g. key: "forwarder.Firefox.local.settings",
            key: "firefoxRelayForwarder",
            target: "object",
            format: "secret-state",
            frame: 512,
            classifier: new bw_PrivateClassifier(),
            state: bw_GENERATOR_DISK,
            initial: bw_firefox_relay_defaultSettings,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
        import: {
            key: "forwarder.Firefox.local.import",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier(["token"]),
            state: bw_GENERATOR_MEMORY,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout", "lock"],
            },
        },
    },
    settings: new bw_UserKeyDefinition(bw_GENERATOR_DISK, "firefoxRelayForwarder", {
        deserializer: (value) => value,
        clearOn: [],
    }),
    importBuffer: new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "firefoxRelayBuffer", {
        deserializer: (value) => value,
        clearOn: ["logout"],
    }),
});
// integration-wide configuration
const bw_FirefoxRelay = Object.freeze({
    id: "firefoxrelay",
    name: "Firefox Relay",
    baseUrl: "https://relay.firefox.com/api",
    selfHost: "never",
    extends: ["forwarder"],
    authenticate(_request, context) {
        return { Authorization: "Token " + context.authenticationToken() };
    },
    forwarder: bw_firefox_relay_forwarder,
});

;// ../../libs/tools/generator/core/src/integration/forward-email.ts




// default values
const bw_forward_email_defaultSettings = Object.freeze({
    token: "",
    domain: "",
});
// supported RPC calls
const bw_forward_email_createForwardingEmail = Object.freeze({
    url(_request, context) {
        const domain = context.emailDomain();
        return context.baseUrl() + `/v1/domains/${domain}/aliases`;
    },
    body(request, context) {
        return {
            labels: context.website(request),
            description: context.generatedBy(request),
        };
    },
    hasJsonPayload(response) {
        return response.status === 200 || response.status === 201;
    },
    processJson(json, context) {
        var _a;
        const { name, domain } = json;
        const domainPart = (_a = domain === null || domain === void 0 ? void 0 : domain.name) !== null && _a !== void 0 ? _a : context.emailDomain();
        return [`${name}@${domainPart}`];
    },
});
// forwarder configuration
const bw_forward_email_forwarder = Object.freeze({
    defaultSettings: bw_forward_email_defaultSettings,
    request: ["token", "domain"],
    settingsConstraints: {
        token: { required: true },
        domain: { required: true },
    },
    local: {
        settings: {
            // FIXME: integration should issue keys at runtime
            // based on integrationId & extension metadata
            // e.g. key: "forwarder.ForwardEmail.local.settings",
            key: "forwardEmailForwarder",
            target: "object",
            format: "secret-state",
            frame: 512,
            classifier: new bw_PrivateClassifier(),
            state: bw_GENERATOR_DISK,
            initial: bw_forward_email_defaultSettings,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
        import: {
            key: "forwarder.ForwardEmail.local.import",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier(["token", "domain"]),
            state: bw_GENERATOR_MEMORY,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout", "lock"],
            },
        },
    },
    settings: new bw_UserKeyDefinition(bw_GENERATOR_DISK, "forwardEmailForwarder", {
        deserializer: (value) => value,
        clearOn: [],
    }),
    importBuffer: new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "forwardEmailBuffer", {
        deserializer: (value) => value,
        clearOn: ["logout"],
    }),
    createForwardingEmail: bw_forward_email_createForwardingEmail,
});
const bw_ForwardEmail = Object.freeze({
    // integration metadata
    id: "forwardemail",
    name: "Forward Email",
    extends: ["forwarder"],
    // service provider
    selfHost: "never",
    baseUrl: "https://api.forwardemail.net",
    authenticate(_request, context) {
        return { Authorization: "Basic " + context.authenticationToken({ base64: true, suffix: ":" }) };
    },
    // specialized configurations
    forwarder: bw_forward_email_forwarder,
});

;// ../../libs/tools/generator/core/src/integration/simple-login.ts




// default values
const bw_simple_login_defaultSettings = Object.freeze({
    token: "",
    domain: "",
    baseUrl: "",
});
// supported RPC calls
const bw_simple_login_createForwardingEmail = Object.freeze({
    url(request, context) {
        const endpoint = context.baseUrl() + "/api/alias/random/new";
        const hostname = context.website(request);
        const url = hostname !== "" ? `${endpoint}?hostname=${hostname}` : endpoint;
        return url;
    },
    body(request, context) {
        return { note: context.generatedBy(request) };
    },
    hasJsonPayload(response) {
        return response.status === 200 || response.status === 201;
    },
    processJson(json) {
        return [json === null || json === void 0 ? void 0 : json.alias];
    },
});
// forwarder configuration
const bw_simple_login_forwarder = Object.freeze({
    defaultSettings: bw_simple_login_defaultSettings,
    createForwardingEmail: bw_simple_login_createForwardingEmail,
    request: ["token", "baseUrl"],
    settingsConstraints: {
        token: { required: true },
    },
    local: {
        settings: {
            // FIXME: integration should issue keys at runtime
            // based on integrationId & extension metadata
            // e.g. key: "forwarder.SimpleLogin.local.settings",
            key: "simpleLoginForwarder",
            target: "object",
            format: "secret-state",
            frame: 512,
            classifier: new bw_PrivateClassifier(),
            state: bw_GENERATOR_DISK,
            initial: bw_simple_login_defaultSettings,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout"],
            },
        },
        import: {
            key: "forwarder.SimpleLogin.local.import",
            target: "object",
            format: "plain",
            classifier: new bw_PublicClassifier(["token", "baseUrl"]),
            state: bw_GENERATOR_MEMORY,
            options: {
                deserializer: (value) => value,
                clearOn: ["logout", "lock"],
            },
        },
    },
    settings: new bw_UserKeyDefinition(bw_GENERATOR_DISK, "simpleLoginForwarder", {
        deserializer: (value) => value,
        clearOn: [],
    }),
    importBuffer: new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "simpleLoginBuffer", {
        deserializer: (value) => value,
        clearOn: ["logout"],
    }),
});
// integration-wide configuration
const bw_SimpleLogin = Object.freeze({
    id: "simplelogin",
    name: "SimpleLogin",
    selfHost: "maybe",
    extends: ["forwarder"],
    baseUrl: "https://app.simplelogin.io",
    authenticate(_request, context) {
        return { Authentication: context.authenticationToken() };
    },
    forwarder: bw_simple_login_forwarder,
});

;// ../../libs/tools/generator/core/src/data/integrations.ts






/** Fixed list of integrations available to the application
 *  @example
 *
 *  // Use `toCredentialGeneratorConfiguration(id :ForwarderIntegration)`
 *  // to convert an integration to a generator configuration
 *  const generator = toCredentialGeneratorConfiguration(Integrations.AddyIo);
 */
const bw_integrations_Integrations = Object.freeze({
    AddyIo: bw_AddyIo,
    DuckDuckGo: bw_DuckDuckGo,
    Fastmail: bw_Fastmail,
    FirefoxRelay: bw_FirefoxRelay,
    ForwardEmail: bw_ForwardEmail,
    SimpleLogin: bw_SimpleLogin,
});
const bw_integrations = new Map(Object.values(bw_integrations_Integrations).map((i) => [i.id, i]));
function bw_integrations_getForwarderConfiguration(id) {
    const maybeForwarder = bw_integrations.get(id);
    if (maybeForwarder && "forwarder" in maybeForwarder) {
        return maybeForwarder;
    }
    else {
        return null;
    }
}

;// ../../libs/tools/generator/core/src/data/policies.ts

/** Policy configurations
 *  @deprecated use Generator.*.policy instead
 */
const bw_Policies = Object.freeze({
    Passphrase: bw_generators_Generators.passphrase.policy,
    Password: bw_generators_Generators.password.policy,
});

;// ../../libs/tools/generator/core/src/data/username-digits.ts
const bw_UsernameDigits = Object.freeze({
    enabled: 4,
    disabled: 0,
});

;// ../../libs/tools/generator/core/src/data/index.ts





















;// ../../libs/tools/generator/core/src/factories.ts
// contains logic that constructs generator services dynamically given
// a generator id.

function bw_createRandomizer(keyService) {
    return new KeyServiceRandomizer(keyService);
}

;// ../../libs/tools/generator/core/src/services/default-generator.service.ts
var bw_default_generator_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/** {@link GeneratorServiceAbstraction} */
class bw_DefaultGeneratorService {
    /** Instantiates the generator service
     * @param strategy tailors the service to a specific generator type
     *            (e.g. password, passphrase)
     * @param policy provides the policy to enforce
     */
    constructor(strategy, policy) {
        this.strategy = strategy;
        this.policy = policy;
        this._evaluators$ = new Map();
    }
    /** {@link GeneratorService.options$} */
    options$(userId) {
        return this.strategy.durableState(userId).state$;
    }
    /** {@link GeneratorService.defaults$} */
    defaults$(userId) {
        return this.strategy.defaults$(userId);
    }
    /** {@link GeneratorService.saveOptions} */
    saveOptions(userId, options) {
        return bw_default_generator_service_awaiter(this, void 0, void 0, function* () {
            yield this.strategy.durableState(userId).update(() => options);
        });
    }
    /** {@link GeneratorService.evaluator$} */
    evaluator$(userId) {
        let evaluator$ = this._evaluators$.get(userId);
        if (!evaluator$) {
            evaluator$ = this.createEvaluator(userId);
            this._evaluators$.set(userId, evaluator$);
        }
        return evaluator$;
    }
    createEvaluator(userId) {
        const evaluator$ = this.policy.getAll$(this.strategy.policy, userId).pipe(
        // create the evaluator from the policies
        this.strategy.toEvaluator());
        return evaluator$;
    }
    /** {@link GeneratorService.enforcePolicy} */
    enforcePolicy(userId, options) {
        return bw_default_generator_service_awaiter(this, void 0, void 0, function* () {
            const policy = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.evaluator$(userId));
            const evaluated = policy.applyPolicy(options);
            const sanitized = policy.sanitize(evaluated);
            return sanitized;
        });
    }
    /** {@link GeneratorService.generate} */
    generate(options) {
        return bw_default_generator_service_awaiter(this, void 0, void 0, function* () {
            return yield this.strategy.generate(options);
        });
    }
}

;// ../../libs/common/src/tools/integration/rpc/rest-client.ts
var bw_rest_client_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
/** Makes remote procedure calls using a RESTful interface. */
class bw_rest_client_RestClient {
    constructor(api, i18n) {
        this.api = api;
        this.i18n = i18n;
    }
    /** uses the fetch API to request a JSON payload. */
    // FIXME: once legacy password generator is removed, replace forwarder-specific error
    //   messages with RPC-generalized ones.
    fetchJson(rpc, params) {
        return bw_rest_client_awaiter(this, void 0, void 0, function* () {
            // run the request
            const request = rpc.toRequest(params);
            const response = yield this.api.nativeFetch(request);
            let result = undefined;
            let errorKey = undefined;
            let errorMessage = undefined;
            const commonError = yield this.detectCommonErrors(response);
            if (commonError) {
                [errorKey, errorMessage] = commonError;
            }
            else if (rpc.hasJsonPayload(response)) {
                [result, errorMessage] = rpc.processJson(yield response.json());
            }
            if (result) {
                return result;
            }
            // handle failures
            errorKey !== null && errorKey !== void 0 ? errorKey : (errorKey = errorMessage ? "forwarderError" : "forwarderUnknownError");
            const error = this.i18n.t(errorKey, rpc.requestor.name, errorMessage);
            throw error;
        });
    }
    detectCommonErrors(response) {
        return bw_rest_client_awaiter(this, void 0, void 0, function* () {
            if (response.status === 401) {
                const message = yield this.tryGetErrorMessage(response);
                const key = message ? "forwaderInvalidTokenWithMessage" : "forwaderInvalidToken";
                return [key, message];
            }
            else if (response.status === 403) {
                const message = yield this.tryGetErrorMessage(response);
                const key = message ? "forwaderInvalidOperationWithMessage" : "forwaderInvalidOperation";
                return [key, message];
            }
            else if (response.status >= 400) {
                const message = yield this.tryGetErrorMessage(response);
                const key = message ? "forwarderError" : "forwarderUnknownError";
                return [key, message];
            }
        });
    }
    tryGetErrorMessage(response) {
        return bw_rest_client_awaiter(this, void 0, void 0, function* () {
            var _a, _b, _c;
            const body = (_a = (yield response.text())) !== null && _a !== void 0 ? _a : "";
            // nullish continues processing; false returns undefined
            // FIXME: inspect content-type header to determine extraction process
            const error = (_c = (_b = this.tryFindErrorAsJson(body)) !== null && _b !== void 0 ? _b : this.tryFindErrorAsText(body)) !== null && _c !== void 0 ? _c : response.statusText;
            return error || undefined;
        });
    }
    tryFindErrorAsJson(body) {
        var _a, _b, _c, _d, _e;
        // tryParse JSON object or string
        const parsable = body.startsWith("{") || body.startsWith(`'`) || body.startsWith(`"`);
        if (!parsable) {
            // fail-and-continue because it's not JSON
            return undefined;
        }
        let parsed = undefined;
        try {
            parsed = JSON.parse(body);
        }
        catch (_f) {
            // fail-and-exit in case `body` is malformed JSON
            return false;
        }
        // could be a string
        if (parsed && typeof parsed === "string") {
            return parsed;
        }
        // could be { error?: T, message?: U }
        const error = (_b = (_a = parsed.error) === null || _a === void 0 ? void 0 : _a.toString()) !== null && _b !== void 0 ? _b : null;
        const message = (_d = (_c = parsed.message) === null || _c === void 0 ? void 0 : _c.toString()) !== null && _d !== void 0 ? _d : null;
        // `false` signals no message found
        const result = error && message ? `${error}: ${message}` : ((_e = error !== null && error !== void 0 ? error : message) !== null && _e !== void 0 ? _e : false);
        return result;
    }
    tryFindErrorAsText(body) {
        if (!body.length || body.includes("<")) {
            return undefined;
        }
        return body;
    }
}

;// ../../libs/common/src/tools/integration/rpc/index.ts







;// ../../libs/common/src/tools/rx.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/** Returns its input. */
function bw_identity(value) {
    return value;
}
/** Combines its arguments into a plain old javascript object. */
function bw_expectedAndActualValue(expectedValue, actualValue) {
    return {
        expectedValue,
        actualValue,
    };
}
/**
 * An observable operator that throws an error when the stream's
 *   value changes. Uses strict (`===`) comparison checks.
 * @param extract a function that identifies the member to compare;
 *   defaults to the identity function
 * @param error a function that packages the expected and failed
 *   values into an error.
 * @returns a stream of values that emits when the input emits,
 *   completes when the input completes, and errors when either the
 *   input errors or the comparison fails.
 */
function bw_errorOnChange(extract = bw_identity, error = bw_expectedAndActualValue) {
    return pipe(startWith(null), pairwise(), map(([expected, actual], i) => {
        // always let the first value through
        if (i === 0) {
            return actual;
        }
        const expectedValue = extract(expected);
        const actualValue = extract(actual);
        // fail the stream if the state desyncs from its initial value
        if (expectedValue === actualValue) {
            return actual;
        }
        else {
            throw error(expectedValue, actualValue);
        }
    }));
}
/**
 * An observable operator that reduces an emitted collection to a single object,
 * returning a default if all items are ignored.
 * @param reduce The reduce function to apply to the filtered collection. The
 *  first argument is the accumulator, and the second is the current item. The
 *  return value is the new accumulator.
 * @param defaultValue The default value to return if the collection is empty. The
 *   default value is also the initial value of the accumulator.
 */
function bw_rx_reduceCollection(reduce, defaultValue) {
    return (0,bw_external_rxjs_namespaceObject.map)((values) => {
        const reduced = (values !== null && values !== void 0 ? values : []).reduce(reduce, structuredClone(defaultValue));
        return reduced;
    });
}
/**
 * An observable operator that emits distinct values by checking that all
 *   values in the previous entry match the next entry. This method emits
 *   when a key is added and does not when a key is removed.
 * @remarks This method checks objects. It does not check items in arrays.
 */
function bw_rx_distinctIfShallowMatch() {
    return (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)((previous, current) => {
        let isDistinct = true;
        for (const key in current) {
            isDistinct && (isDistinct = previous[key] === current[key]);
        }
        return isDistinct;
    });
}
/** Create an observable that, once subscribed, emits `true` then completes when
 *   any input completes. If an input is already complete when the subscription
 *   occurs, it emits immediately.
 *  @param watch$ the observable(s) to watch for completion; if an array is passed,
 *   null and undefined members are ignored. If `watch$` is empty, `anyComplete`
 *   will never complete.
 *  @returns An observable that emits `true` when any of its inputs
 *   complete. The observable forwards the first error from its input.
 *  @remarks This method is particularly useful in combination with `takeUntil` and
 *   streams that are not guaranteed to complete on their own.
 */
function bw_rx_anyComplete(watch$) {
    if (Array.isArray(watch$)) {
        const completes$ = watch$
            .filter((w$) => !!w$)
            .map((w$) => w$.pipe((0,bw_external_rxjs_namespaceObject.ignoreElements)(), (0,bw_external_rxjs_namespaceObject.endWith)(true)));
        const completed$ = (0,bw_external_rxjs_namespaceObject.race)(completes$);
        return completed$;
    }
    else {
        return watch$.pipe((0,bw_external_rxjs_namespaceObject.ignoreElements)(), (0,bw_external_rxjs_namespaceObject.endWith)(true));
    }
}
/**
 * Create an observable that delays the input stream until all watches have
 *  emitted a value. The watched values are not included in the source stream.
 *  The last emission from the source is output when all the watches have
 *  emitted at least once.
 * @param watch$ the observable(s) to watch for readiness. If `watch$` is empty,
 *  `ready` will never emit.
 * @returns An observable that emits when the source stream emits. The observable
 *   errors if one of its watches completes before emitting. It also errors if one
 *   of its watches errors.
 */
function bw_ready(watch$) {
    const watching$ = Array.isArray(watch$) ? watch$ : [watch$];
    return (0,bw_external_rxjs_namespaceObject.pipe)((0,bw_external_rxjs_namespaceObject.connect)((source$) => {
        // this subscription is safe because `source$` connects only after there
        // is an external subscriber.
        const source = new bw_external_rxjs_namespaceObject.ReplaySubject(1);
        source$.subscribe(source);
        // `concat` is subscribed immediately after it's returned, at which point
        // `zip` blocks until all items in `watching$` are ready. If that occurs
        // after `source$` is hot, then the replay subject sends the last-captured
        // emission through immediately. Otherwise, `ready` waits for the next
        // emission
        return (0,bw_external_rxjs_namespaceObject.concat)((0,bw_external_rxjs_namespaceObject.zip)(watching$).pipe((0,bw_external_rxjs_namespaceObject.first)(), (0,bw_external_rxjs_namespaceObject.ignoreElements)()), source).pipe((0,bw_external_rxjs_namespaceObject.takeUntil)(bw_rx_anyComplete(source)));
    }));
}
function bw_rx_withLatestReady(watch$) {
    return (0,bw_external_rxjs_namespaceObject.connect)((source$) => {
        // these subscriptions are safe because `source$` connects only after there
        // is an external subscriber.
        const source = new bw_external_rxjs_namespaceObject.ReplaySubject(1);
        source$.subscribe(source);
        const watch = new bw_external_rxjs_namespaceObject.ReplaySubject(1);
        watch$.subscribe(watch);
        // `concat` is subscribed immediately after it's returned, at which point
        // `zip` blocks until all items in `watching$` are ready. If that occurs
        // after `source$` is hot, then the replay subject sends the last-captured
        // emission through immediately. Otherwise, `ready` waits for the next
        // emission
        return (0,bw_external_rxjs_namespaceObject.concat)((0,bw_external_rxjs_namespaceObject.zip)(watch).pipe((0,bw_external_rxjs_namespaceObject.first)(), (0,bw_external_rxjs_namespaceObject.ignoreElements)()), source).pipe((0,bw_external_rxjs_namespaceObject.withLatestFrom)(watch), (0,bw_external_rxjs_namespaceObject.takeUntil)(bw_rx_anyComplete(source)));
    });
}
/**
 * Create an observable that emits the latest value of the source stream
 *  when `watch$` emits. If `watch$` emits before the stream emits, then
 *  an emission occurs as soon as a value becomes ready.
 * @param watch$ the observable that triggers emissions
 * @returns An observable that emits when `watch$` emits. The observable
 *  errors if its source stream errors. It also errors if `on` errors. It
 *  completes if its watch completes.
 *
 * @remarks This works like `audit`, but it repeats emissions when
 *  watch$ fires.
 */
function bw_on(watch$) {
    return pipe(connect((source$) => {
        const source = new ReplaySubject(1);
        source$.subscribe(source);
        return watch$
            .pipe(bw_ready(source), concatMap(() => source.pipe(first())))
            .pipe(takeUntil(bw_rx_anyComplete(source)));
    }));
}
/** Create an observable that emits the first value from the source and
 *  throws if the observable emits another value.
 *  @param options.name names the pin to make discovering failing observables easier
 *  @param options.distinct compares two emissions with each other to determine whether
 *   the second emission is a duplicate. When this is specified, duplicates are ignored.
 *   When this isn't specified, any emission after the first causes the pin to throw
 *   an error.
 */
function bw_pin(options) {
    return (0,bw_external_rxjs_namespaceObject.pipe)((options === null || options === void 0 ? void 0 : options.distinct) ? (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(options.distinct) : (i) => i, (0,bw_external_rxjs_namespaceObject.map)((value, index) => {
        var _a, _b;
        if (index > 0) {
            throw new Error(`${(_b = (_a = options === null || options === void 0 ? void 0 : options.name) === null || _a === void 0 ? void 0 : _a.call(options)) !== null && _b !== void 0 ? _b : "unknown"} observable should only emit one value.`);
        }
        else {
            return value;
        }
    }));
}

;// ../../libs/common/src/tools/state/classified-format.ts
function bw_isClassifiedFormat(value) {
    return (!!value &&
        "id" in value &&
        "secret" in value &&
        "disclosed" in value &&
        typeof value.secret === "string" &&
        typeof value.disclosed === "object");
}

;// ../../libs/common/src/tools/state/object-key.ts

/** Performs a type inference that identifies object keys. */
function bw_isObjectKey(key) {
    return key.target === "object" && "format" in key && "classifier" in key;
}
/** Converts an object key to a plaform-compatible `UserKeyDefinition`. */
function bw_toUserKeyDefinition(key) {
    if (key.format === "plain") {
        const plain = new bw_UserKeyDefinition(key.state, key.key, key.options);
        return plain;
    }
    else if (key.format === "classified") {
        const classified = new bw_UserKeyDefinition(key.state, key.key, {
            cleanupDelayMs: key.options.cleanupDelayMs,
            deserializer: (jsonValue) => jsonValue,
            clearOn: key.options.clearOn,
        });
        return classified;
    }
    else if (key.format === "secret-state") {
        const classified = new bw_UserKeyDefinition(key.state, key.key, {
            cleanupDelayMs: key.options.cleanupDelayMs,
            deserializer: (jsonValue) => jsonValue,
            clearOn: key.options.clearOn,
        });
        return classified;
    }
    else {
        throw new Error(`unknown format: ${key.format}`);
    }
}

;// ../../libs/common/src/tools/state/state-constraints-dependency.ts
/** Returns `true` if the input constraint is a `DynamicStateConstraints<T>`.
 *  Otherwise, returns false.
 *  @param constraints the constraint to evaluate.
 * */
function bw_isDynamic(constraints) {
    return constraints && "calibrate" in constraints;
}

;// ../../libs/common/src/tools/state/user-state-subject.ts
var bw_user_state_subject_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







// FIXME: The subject should always repeat the value when it's own `next` method is called.
//
// Chrome StateService only calls `next` when the underlying values changes. When enforcing,
// say, a minimum constraint, any value beneath the minimum becomes the minimum. This prevents
// invalid data received in sequence from calling `next` because the state provider doesn't
// emit.
//
// The hack is pretty simple. Insert arbitrary data into the saved data to ensure
// that it *always* changes.
//
// Any real fix will be fairly complex because it needs to recognize *fast* when it
// is waiting. Alternatively, the kludge could become a format properly fed by random noise.
//
// NOTE: this only matters for plaintext objects; encrypted fields change with every
//   update b/c their IVs change.
const bw_ALWAYS_UPDATE_KLUDGE = "$^$ALWAYS_UPDATE_KLUDGE_PROPERTY$^$";
/** Default frame size for data packing */
const bw_DEFAULT_FRAME_SIZE = 32;
/**
 * Adapt a state provider to an rxjs subject.
 *
 * This subject buffers the last value it received in memory. The buffer is erased
 * if the subject receives a complete or error event. It does not persist the buffer.
 *
 * Warning! The user state subject has a synchronous interface, but subscriptions are
 * always asynchronous.
 *
 * @template State the state stored by the subject
 * @template Dependencies use-specific dependencies provided by the user.
 */
class bw_user_state_subject_UserStateSubject extends bw_external_rxjs_namespaceObject.Observable {
    /**
     * Instantiates the user state subject bound to a persistent backing store
     * @param key identifies the persistent backing store
     * @param getState creates a persistent backing store using a key
     * @param context tailor the subject's behavior for a particular
     *   purpose.
     * @param dependencies.when$ blocks updates to the state subject until
     *   this becomes true. When this occurs, only the last-received update
     *   is applied. The blocked update is kept in memory. It does not persist
     *   to disk.
     * @param dependencies.account$ writes block until the account$
     *   is available.
     */
    constructor(key, providers, context) {
        var _a, _b, _c;
        super();
        this.key = key;
        this.providers = providers;
        this.context = context;
        // using subjects to ensure the right semantics are followed;
        // if greater efficiency becomes desirable, consider implementing
        // `SubjectLike` directly
        this.input = new bw_external_rxjs_namespaceObject.ReplaySubject(1);
        this.output = new bw_external_rxjs_namespaceObject.ReplaySubject(1);
        this.counter = 0;
        if (bw_isObjectKey(this.key)) {
            // classification and encryption only supported with `ObjectKey`
            this.objectKey = this.key;
            this.stateKey = bw_toUserKeyDefinition(this.key);
        }
        else {
            // raw state access granted with `UserKeyDefinition`
            this.objectKey = null;
            this.stateKey = this.key;
        }
        this.log = this.providers.log({
            contextId: this.contextId,
            type: "UserStateSubject",
            storage: {
                state: this.stateKey.stateDefinition.name,
                key: this.stateKey.key,
            },
        });
        // normalize dependencies
        const when$ = ((_a = this.context.when$) !== null && _a !== void 0 ? _a : new bw_external_rxjs_namespaceObject.BehaviorSubject(true)).pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)());
        const account$ = context.account$.pipe(bw_pin({
            name: () => `${this.contextId} { account$ }`,
            distinct(prev, current) {
                return prev.id === current.id;
            },
        }), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        const encryptor$ = this.encryptor(account$);
        const constraints$ = ((_b = this.context.constraints$) !== null && _b !== void 0 ? _b : bw_unconstrained$()).pipe((0,bw_external_rxjs_namespaceObject.catchError)((e) => {
            this.log.error(e, "constraints$ dependency failed; using last-known constraints");
            return bw_external_rxjs_namespaceObject.EMPTY;
        }), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        const dependencies$ = ((_c = this.context.dependencies$) !== null && _c !== void 0 ? _c : new bw_external_rxjs_namespaceObject.BehaviorSubject(null)).pipe((0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        // load state once the account becomes available
        const userState$ = account$.pipe((0,bw_external_rxjs_namespaceObject.tap)((account) => this.log.debug({ accountId: account.id }, "loading user state")), (0,bw_external_rxjs_namespaceObject.map)((account) => this.providers.state.getUser(account.id, this.stateKey)), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        // wire output before input so that output normalizes the current state
        // before any `next` value is processed
        this.outputSubscription = userState$
            .pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userState) => userState.state$), this.declassify(encryptor$), this.adjust((0,bw_external_rxjs_namespaceObject.combineLatestWith)(constraints$)), (0,bw_external_rxjs_namespaceObject.takeUntil)(bw_rx_anyComplete(account$)))
            .subscribe(this.output);
        const last$ = new bw_external_rxjs_namespaceObject.ReplaySubject(1);
        this.output
            .pipe((0,bw_external_rxjs_namespaceObject.last)(), (0,bw_external_rxjs_namespaceObject.map)((o) => o.state))
            .subscribe(last$);
        // the update stream simulates the stateProvider's "shouldUpdate"
        // functionality & applies policy
        const updates$ = (0,bw_external_rxjs_namespaceObject.concat)(this.input.pipe(this.when(when$), this.adjust(bw_rx_withLatestReady(constraints$)), this.prepareUpdate(this, dependencies$)), 
        // when the output subscription completes, its last-emitted value
        // loops around to the input for finalization
        last$.pipe(this.fix(constraints$), this.prepareUpdate(last$, dependencies$)));
        // classification/encryption bound to the input subscription's lifetime
        // to ensure that `fix` has access to the encryptor key
        //
        // FIXME: this should probably timeout when a lock occurs
        this.inputSubscription = updates$
            .pipe(this.classify(encryptor$), (0,bw_external_rxjs_namespaceObject.withLatestFrom)(userState$), (0,bw_external_rxjs_namespaceObject.takeUntil)(bw_rx_anyComplete([when$, this.input, encryptor$])))
            .subscribe({
            next: ([input, state]) => this.onNext(input, state),
            error: (e) => this.onError(e),
            complete: () => this.onComplete(),
        });
    }
    get contextId() {
        return `UserStateSubject(${this.stateKey.stateDefinition.name}, ${this.stateKey.key})`;
    }
    encryptor(account$) {
        var _a, _b;
        const singleUserId$ = account$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account.id));
        const frameSize = (_b = (_a = this.objectKey) === null || _a === void 0 ? void 0 : _a.frame) !== null && _b !== void 0 ? _b : bw_DEFAULT_FRAME_SIZE;
        const encryptor$ = this.providers.encryptor.userEncryptor$(frameSize, { singleUserId$ }).pipe((0,bw_external_rxjs_namespaceObject.tap)(() => this.log.debug("encryptor constructed")), (0,bw_external_rxjs_namespaceObject.map)(({ encryptor }) => encryptor), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        return encryptor$;
    }
    when(when$) {
        return (0,bw_external_rxjs_namespaceObject.pipe)((0,bw_external_rxjs_namespaceObject.combineLatestWith)(when$.pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)())), (0,bw_external_rxjs_namespaceObject.tap)(([_, when]) => this.log.debug({ when }, "when status")), (0,bw_external_rxjs_namespaceObject.filter)(([_, when]) => !!when), (0,bw_external_rxjs_namespaceObject.map)(([input]) => input));
    }
    prepareUpdate(init$, dependencies$) {
        return (input$) => (0,bw_external_rxjs_namespaceObject.concat)(
        // `init$` becomes the accumulator for `scan`
        init$.pipe((0,bw_external_rxjs_namespaceObject.first)(), (0,bw_external_rxjs_namespaceObject.map)((init) => [init, null])), input$.pipe((0,bw_external_rxjs_namespaceObject.map)((constrained) => constrained.state), (0,bw_external_rxjs_namespaceObject.withLatestFrom)(dependencies$))).pipe(
        // scan only emits values that can cause updates
        (0,bw_external_rxjs_namespaceObject.scan)(([prev], [pending, dependencies]) => {
            var _a, _b, _c, _d, _e, _f;
            const shouldUpdate = (_c = (_b = (_a = this.context).shouldUpdate) === null || _b === void 0 ? void 0 : _b.call(_a, prev, pending, dependencies)) !== null && _c !== void 0 ? _c : true;
            if (shouldUpdate) {
                // actual update
                const next = (_f = (_e = (_d = this.context).nextValue) === null || _e === void 0 ? void 0 : _e.call(_d, prev, pending, dependencies)) !== null && _f !== void 0 ? _f : pending;
                return [next, dependencies];
            }
            else {
                // false update
                this.log.debug("shouldUpdate prevented write");
                return [prev, null];
            }
        }), 
        // the first emission primes `scan`s aggregator
        (0,bw_external_rxjs_namespaceObject.skip)(1), (0,bw_external_rxjs_namespaceObject.map)(([state]) => state), 
        // clean up false updates
        (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)());
    }
    adjust(withConstraints) {
        return (0,bw_external_rxjs_namespaceObject.pipe)(
        // how constraints are blended with incoming emissions varies:
        // * `output` needs to emit when constraints update
        // * `input` needs to wait until a message flows through the pipe
        withConstraints, (0,bw_external_rxjs_namespaceObject.map)(([loadedState, constraints]) => {
            var _a;
            if (!loadedState && !((_a = this.objectKey) === null || _a === void 0 ? void 0 : _a.initial)) {
                this.log.debug("no value; bypassing adjustment");
                return {
                    constraints: {},
                    state: null,
                };
            }
            this.log.debug("adjusting");
            const unconstrained = loadedState !== null && loadedState !== void 0 ? loadedState : structuredClone(this.objectKey.initial);
            const calibration = bw_isDynamic(constraints)
                ? constraints.calibrate(unconstrained)
                : constraints;
            const adjusted = calibration.adjust(unconstrained);
            this.log.debug("adjusted");
            return {
                constraints: calibration.constraints,
                state: adjusted,
            };
        }));
    }
    fix(constraints$) {
        return (0,bw_external_rxjs_namespaceObject.pipe)((0,bw_external_rxjs_namespaceObject.combineLatestWith)(constraints$), (0,bw_external_rxjs_namespaceObject.map)(([loadedState, constraints]) => {
            this.log.debug("fixing");
            const calibration = bw_isDynamic(constraints)
                ? constraints.calibrate(loadedState)
                : constraints;
            const fixed = calibration.fix(loadedState);
            this.log.debug("fixed");
            return {
                constraints: calibration.constraints,
                state: fixed,
            };
        }));
    }
    declassify(encryptor$) {
        // short-circuit if they key lacks encryption support
        if (!this.objectKey || this.objectKey.format === "plain") {
            this.log.debug("key uses plain format; bypassing declassification");
            return (input$) => input$;
        }
        // all other keys support encryption; enable encryptor support
        return (0,bw_external_rxjs_namespaceObject.pipe)(this.mapToClassifiedFormat(), (0,bw_external_rxjs_namespaceObject.combineLatestWith)(encryptor$), (0,bw_external_rxjs_namespaceObject.concatMap)((_a) => bw_user_state_subject_awaiter(this, [_a], void 0, function* ([input, encryptor]) {
            // pass through null values
            if (input === null || input === undefined) {
                this.log.debug("no value; bypassing declassification");
                return null;
            }
            this.log.debug("declassifying");
            // decrypt classified data
            const { secret, disclosed } = input;
            const encrypted = bw_enc_string_EncString.fromJSON(secret);
            const decryptedSecret = yield encryptor.decrypt(encrypted);
            // assemble into proper state
            const declassified = this.objectKey.classifier.declassify(disclosed, decryptedSecret);
            const state = this.objectKey.options.deserializer(declassified);
            this.log.debug("declassified");
            return state;
        })));
    }
    mapToClassifiedFormat() {
        // FIXME: warn when data is dropped in the console and/or report an error
        //   through the observable; consider redirecting dropped data to a recovery
        //   location
        // user-state subject's default format is object-aware
        if (this.objectKey && this.objectKey.format === "classified") {
            return (0,bw_external_rxjs_namespaceObject.map)((input) => {
                if (!bw_isClassifiedFormat(input)) {
                    this.log.warn("classified data must be in classified format; dropping");
                    return null;
                }
                return input;
            });
        }
        // secret state's format wraps objects in an array
        if (this.objectKey && this.objectKey.format === "secret-state") {
            return (0,bw_external_rxjs_namespaceObject.map)((input) => {
                if (!Array.isArray(input)) {
                    this.log.warn("secret-state requires array formatting; dropping");
                    return null;
                }
                const [unwrapped] = input;
                if (!bw_isClassifiedFormat(unwrapped)) {
                    this.log.warn("unwrapped secret-state must be in classified format; dropping");
                    return null;
                }
                return unwrapped;
            });
        }
        this.log.panic({ format: this.objectKey.format }, "unsupported serialization format");
    }
    classify(encryptor$) {
        // short-circuit if they key lacks encryption support; `encryptor` is
        // readied to preserve `dependencies.singleUserId$` emission contract
        if (!this.objectKey || this.objectKey.format === "plain") {
            this.log.debug("key uses plain format; bypassing classification");
            return (0,bw_external_rxjs_namespaceObject.pipe)(bw_ready(encryptor$), (0,bw_external_rxjs_namespaceObject.map)((input) => input));
        }
        // all other keys support encryption; enable encryptor support
        return (0,bw_external_rxjs_namespaceObject.pipe)(bw_rx_withLatestReady(encryptor$), (0,bw_external_rxjs_namespaceObject.concatMap)((_a) => bw_user_state_subject_awaiter(this, [_a], void 0, function* ([input, encryptor]) {
            // fail fast if there's no value
            if (input === null || input === undefined) {
                this.log.debug("no value; bypassing classification");
                return null;
            }
            this.log.debug("classifying");
            // split data by classification level
            const serialized = JSON.parse(JSON.stringify(input));
            const classified = this.objectKey.classifier.classify(serialized);
            // protect data
            const encrypted = yield encryptor.encrypt(classified.secret);
            const secret = JSON.parse(JSON.stringify(encrypted));
            // wrap result in classified format envelope for storage
            const envelope = {
                id: null,
                secret,
                disclosed: classified.disclosed,
            };
            this.log.debug("classified");
            // deliberate type erasure; the type is restored during `declassify`
            return envelope;
        })), this.mapToStorageFormat());
    }
    mapToStorageFormat() {
        // user-state subject's default format is object-aware
        if (this.objectKey && this.objectKey.format === "classified") {
            return (0,bw_external_rxjs_namespaceObject.map)((input) => input);
        }
        // secret state's format wraps objects in an array
        if (this.objectKey && this.objectKey.format === "secret-state") {
            return (0,bw_external_rxjs_namespaceObject.map)((input) => [input]);
        }
        this.log.panic({ format: this.objectKey.format }, "unsupported serialization format");
    }
    next(value) {
        var _a;
        (_a = this.input) === null || _a === void 0 ? void 0 : _a.next(value);
    }
    error(err) {
        var _a;
        (_a = this.input) === null || _a === void 0 ? void 0 : _a.error(err);
    }
    complete() {
        var _a;
        (_a = this.input) === null || _a === void 0 ? void 0 : _a.complete();
    }
    /** Subscribe to the subject's event stream
     * @param observer listening for events
     * @returns the subscription
     */
    subscribe(observer) {
        return this.output.pipe((0,bw_external_rxjs_namespaceObject.map)((wc) => wc.state)).subscribe(observer);
    }
    /** A stream containing settings and their last-applied constraints. */
    get withConstraints$() {
        return this.output.asObservable();
    }
    onNext(value, state) {
        state
            .update(() => {
            this.log.debug("updating");
            if (typeof value === "object") {
                // related: ALWAYS_UPDATE_KLUDGE FIXME
                const counter = this.counter++;
                if (counter > Number.MAX_SAFE_INTEGER) {
                    this.counter = 0;
                }
                const kludge = Object.assign({}, value);
                kludge[bw_ALWAYS_UPDATE_KLUDGE] = counter;
            }
            this.log.debug("updated");
            return value;
        })
            .catch((e) => {
            this.log.error(e, "updating failed");
            this.onError(e);
        });
    }
    onError(value) {
        if (!this.isDisposed) {
            this.log.debug(value, "forwarding error to subscribers");
            this.output.error(value);
        }
        this.dispose();
    }
    onComplete() {
        if (!this.isDisposed) {
            this.output.complete();
        }
        this.dispose();
    }
    get isDisposed() {
        return this.input === null;
    }
    dispose() {
        var _a, _b;
        if (!this.isDisposed) {
            this.log.debug("disposing");
            // clean up internal subscriptions
            (_a = this.inputSubscription) === null || _a === void 0 ? void 0 : _a.unsubscribe();
            (_b = this.outputSubscription) === null || _b === void 0 ? void 0 : _b.unsubscribe();
            this.inputSubscription = null;
            this.outputSubscription = null;
            // drop input to ensure its value is removed from memory
            this.input = null;
            this.log.debug("disposed");
        }
    }
}

;// ../../libs/tools/generator/core/src/policies/available-algorithms-policy.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/** Reduces policies to a set of available algorithms
 *  @param policies the policies to reduce
 *  @returns the resulting `AlgorithmAvailabilityPolicy`
 */
function bw_available_algorithms_policy_availableAlgorithms(policies) {
    const overridePassword = policies
        .filter((policy) => policy.type === PolicyType.PasswordGenerator && policy.enabled)
        .reduce((type, policy) => { var _a; return (type === "password" ? type : ((_a = policy.data.overridePasswordType) !== null && _a !== void 0 ? _a : type)); }, null);
    const policy = [...EmailAlgorithms, ...UsernameAlgorithms];
    if (overridePassword) {
        policy.push(overridePassword);
    }
    else {
        policy.push(...PasswordAlgorithms);
    }
    return policy;
}

;// ../../libs/tools/generator/core/src/rx.ts



/** Maps an administrative console policy to a policy evaluator using the provided configuration.
 *  @param configuration the configuration that constructs the evaluator.
 */
function bw_mapPolicyToEvaluator(configuration) {
    return (0,bw_external_rxjs_namespaceObject.pipe)(bw_rx_reduceCollection(configuration.combine, configuration.disabledValue), bw_rx_distinctIfShallowMatch(), (0,bw_external_rxjs_namespaceObject.map)(configuration.createEvaluator));
}
/** Maps an administrative console policy to constraints using the provided configuration.
 *  @param configuration the configuration that constructs the constraints.
 */
function bw_rx_mapPolicyToConstraints(configuration, email) {
    return pipe(reduceCollection(configuration.combine, configuration.disabledValue), distinctIfShallowMatch(), map((policy) => configuration.toConstraints(policy, email)));
}
/** Constructs a method that maps a policy to the default (no-op) policy. */
function bw_newDefaultEvaluator() {
    return () => {
        return (0,bw_external_rxjs_namespaceObject.pipe)((0,bw_external_rxjs_namespaceObject.map)((_) => new bw_default_policy_evaluator_DefaultPolicyEvaluator()));
    };
}

;// ../../libs/tools/generator/core/src/services/credential-preferences.ts


/** plaintext password generation options */
const bw_credential_preferences_PREFERENCES = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "credentialPreferences", {
    deserializer: (value) => {
        var _a, _b;
        const result = (_a = value) !== null && _a !== void 0 ? _a : {};
        for (const key in bw_DefaultCredentialPreferences) {
            // bind `key` to `category` to transmute the type
            const category = key;
            const preference = (_b = result[category]) !== null && _b !== void 0 ? _b : Object.assign({}, bw_DefaultCredentialPreferences[category]);
            if (typeof preference.updated === "string") {
                preference.updated = new Date(preference.updated);
            }
            result[category] = preference;
        }
        return result;
    },
    clearOn: ["logout"],
});

;// ../../libs/tools/generator/core/src/services/credential-generator.service.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










class bw_CredentialGeneratorService {
    constructor(randomizer, policyService, apiService, i18nService, providers) {
        this.randomizer = randomizer;
        this.policyService = policyService;
        this.apiService = apiService;
        this.i18nService = i18nService;
        this.providers = providers;
    }
    getDependencyProvider() {
        return {
            client: new RestClient(this.apiService, this.i18nService),
            i18nService: this.i18nService,
            randomizer: this.randomizer,
        };
    }
    // FIXME: the rxjs methods of this service can be a lot more resilient if
    // `Subjects` are introduced where sharing occurs
    /** Generates a stream of credentials
     * @param configuration determines which generator's settings are loaded
     * @param dependencies.on$ Required. A new credential is emitted when this emits.
     */
    generate$(configuration, dependencies) {
        const engine = configuration.engine.create(this.getDependencyProvider());
        const settings$ = this.settings$(configuration, dependencies);
        // generation proper
        const generate$ = dependencies.on$.pipe(withLatestReady(settings$), concatMap(([request, settings]) => engine.generate(request, settings)), takeUntil(anyComplete([settings$])));
        return generate$;
    }
    algorithms$(category, dependencies) {
        // any cast required here because TypeScript fails to bind `category`
        // to the union-typed overload of `algorithms`.
        const algorithms = this.algorithms(category);
        // apply policy
        const algorithms$ = dependencies.account$.pipe(distinctUntilChanged(), switchMap((account) => {
            const policies$ = this.policyService.getAll$(PolicyType.PasswordGenerator, account.id).pipe(map((p) => new Set(availableAlgorithms(p))), 
            // complete policy emissions otherwise `switchMap` holds `algorithms$` open indefinitely
            takeUntil(anyComplete(dependencies.account$)));
            return policies$;
        }), map((available) => {
            const filtered = algorithms.filter((c) => isForwarderIntegration(c.id) || available.has(c.id));
            return filtered;
        }));
        return algorithms$;
    }
    algorithms(category) {
        const categories = Array.isArray(category) ? category : [category];
        const algorithms = categories
            .flatMap((c) => CredentialCategories[c])
            .map((id) => this.algorithm(id))
            .filter((info) => info !== null);
        const forwarders = Object.keys(Integrations)
            .map((key) => {
            const forwarder = { forwarder: Integrations[key].id };
            return this.algorithm(forwarder);
        })
            .filter((forwarder) => categories.includes(forwarder.category));
        return algorithms.concat(forwarders);
    }
    /** Look up the metadata for a specific generator algorithm
     *  @param id identifies the algorithm
     *  @returns the requested metadata, or `null` if the metadata wasn't found.
     */
    algorithm(id) {
        let generator = null;
        let integration = null;
        if (isForwarderIntegration(id)) {
            const forwarderConfig = getForwarderConfiguration(id.forwarder);
            integration = forwarderConfig;
            if (forwarderConfig) {
                generator = toCredentialGeneratorConfiguration(forwarderConfig);
            }
        }
        else {
            generator = Generators[id];
        }
        if (!generator) {
            throw new Error(`Invalid credential algorithm: ${JSON.stringify(id)}`);
        }
        const info = {
            id: generator.id,
            category: generator.category,
            name: integration ? integration.name : this.i18nService.t(generator.nameKey),
            generate: this.i18nService.t(generator.generateKey),
            onGeneratedMessage: this.i18nService.t(generator.onGeneratedMessageKey),
            credentialType: this.i18nService.t(generator.credentialTypeKey),
            copy: this.i18nService.t(generator.copyKey),
            useGeneratedValue: this.i18nService.t(generator.useGeneratedValueKey),
            onlyOnRequest: generator.onlyOnRequest,
            request: generator.request,
        };
        if (generator.descriptionKey) {
            info.description = this.i18nService.t(generator.descriptionKey);
        }
        return info;
    }
    /** Get the settings for the provided configuration
     * @param configuration determines which generator's settings are loaded
     * @param dependencies.account$ identifies the account to which the settings are bound.
     * @returns an observable that emits settings
     * @remarks the observable enforces policies on the settings
     */
    settings$(configuration, dependencies) {
        const constraints$ = this.policy$(configuration, dependencies);
        const settings = new UserStateSubject(configuration.settings.account, this.providers, {
            constraints$,
            account$: dependencies.account$,
        });
        const settings$ = settings.pipe(map((settings) => settings !== null && settings !== void 0 ? settings : structuredClone(configuration.settings.initial)));
        return settings$;
    }
    /** Get a subject bound to credential generator preferences.
     *  @param dependencies.account$ identifies the account to which the preferences are bound
     *  @returns a subject bound to the user's preferences
     *  @remarks Preferences determine which algorithms are used when generating a
     *   credential from a credential category (e.g. `PassX` or `Username`). Preferences
     *   should not be used to hold navigation history. Use @bitwarden/generator-navigation
     *   instead.
     */
    preferences(dependencies) {
        // FIXME: enforce policy
        const subject = new UserStateSubject(PREFERENCES, this.providers, dependencies);
        return subject;
    }
    /** Get a subject bound to a specific user's settings
     * @param configuration determines which generator's settings are loaded
     * @param dependencies.account$ identifies the account to which the settings are bound
     * @returns a subject bound to the requested user's generator settings
     * @remarks the subject enforces policy for the settings
     */
    settings(configuration, dependencies) {
        const constraints$ = this.policy$(configuration, dependencies);
        const subject = new UserStateSubject(configuration.settings.account, this.providers, {
            constraints$,
            account$: dependencies.account$,
        });
        return subject;
    }
    /** Get the policy constraints for the provided configuration
     *  @param dependencies.account$ determines which user's policy is loaded
     *  @returns an observable that emits the policy once `dependencies.account$`
     *   and the policy become available.
     */
    policy$(configuration, dependencies) {
        const constraints$ = dependencies.account$.pipe(map((account) => {
            if (account.emailVerified) {
                return { userId: account.id, email: account.email };
            }
            return { userId: account.id, email: null };
        }), switchMap(({ userId, email }) => {
            // complete policy emissions otherwise `switchMap` holds `policies$` open indefinitely
            const policies$ = this.policyService
                .getAll$(configuration.policy.type, userId)
                .pipe(mapPolicyToConstraints(configuration.policy, email), takeUntil(anyComplete(dependencies.account$)));
            return policies$;
        }));
        return constraints$;
    }
}

;// ../../libs/tools/generator/core/src/services/index.ts



;// ../../libs/tools/generator/core/src/integration/index.ts







;// ../../libs/common/src/tools/cryptography/user-encryptor.abstraction.ts
/** An encryption strategy that protects a type's secrets with
 *  user-specific keys. This strategy is bound to a specific user.
 */
class bw_UserEncryptor {
}

;// ../../libs/common/src/tools/cryptography/user-key-encryptor.ts
var bw_user_key_encryptor_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

/** A classification strategy that protects a type's secrets by encrypting them
 *  with a `UserKey`
 */
class bw_UserKeyEncryptor extends bw_UserEncryptor {
    /** Instantiates the encryptor
     *  @param userId identifies the user bound to the encryptor.
     *  @param encryptService protects properties of `Secret`.
     *  @param keyService looks up the user key when protecting data.
     *  @param dataPacker packs and unpacks data classified as secrets.
     */
    constructor(userId, encryptService, key, dataPacker) {
        super();
        this.userId = userId;
        this.encryptService = encryptService;
        this.key = key;
        this.dataPacker = dataPacker;
        this.assertHasValue("userId", userId);
        this.assertHasValue("key", key);
        this.assertHasValue("dataPacker", dataPacker);
        this.assertHasValue("encryptService", encryptService);
    }
    encrypt(secret) {
        return bw_user_key_encryptor_awaiter(this, void 0, void 0, function* () {
            this.assertHasValue("secret", secret);
            let packed = this.dataPacker.pack(secret);
            const encrypted = yield this.encryptService.encrypt(packed, this.key);
            packed = null;
            return encrypted;
        });
    }
    decrypt(secret) {
        return bw_user_key_encryptor_awaiter(this, void 0, void 0, function* () {
            this.assertHasValue("secret", secret);
            let decrypted = yield this.encryptService.decryptToUtf8(secret, this.key);
            const unpacked = this.dataPacker.unpack(decrypted);
            decrypted = null;
            return unpacked;
        });
    }
    assertHasValue(name, value) {
        if (value === undefined || value === null) {
            throw new Error(`${name} cannot be null or undefined`);
        }
    }
}

;// ../../libs/common/src/tools/state/buffered-state.ts
var bw_buffered_state_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/** Stateful storage that overwrites one state with a buffered state.
 *  When a overwrite occurs, the input state is automatically deleted.
 *  @remarks The buffered state can only overwrite non-nullish values. If the
 *   buffer key contains `null` or `undefined`, it will do nothing.
 */
class bw_BufferedState {
    /**
     * Instantiate a buffered state
     * @param provider constructs the buffer.
     * @param key defines the buffer location.
     * @param output updates when a overwrite occurs
     * @param dependency$ provides data the buffer depends upon to evaluate and
     *   transform its data. If this is omitted, then `true` is injected as
     *   a dependency, which with a default output will trigger a overwrite immediately.
     *
     * @remarks `dependency$` enables overwrite control during dynamic circumstances,
     *   such as when a overwrite should occur only if a user key is available.
     */
    constructor(provider, key, output, dependency$ = null) {
        this.key = key;
        this.output = output;
        this.bufferedState = provider.getUser(output.userId, key.toKeyDefinition());
        // overwrite the output value
        const hasValue$ = (0,bw_external_rxjs_namespaceObject.concat)((0,bw_external_rxjs_namespaceObject.of)(null), this.bufferedState.state$).pipe((0,bw_external_rxjs_namespaceObject.map)((buffer) => (buffer !== null && buffer !== void 0 ? buffer : null) !== null));
        const overwriteDependency$ = (dependency$ !== null && dependency$ !== void 0 ? dependency$ : (0,bw_external_rxjs_namespaceObject.of)(true)).pipe((0,bw_external_rxjs_namespaceObject.map)((dependency) => [key.shouldOverwrite(dependency), dependency]));
        const overwrite$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([hasValue$, overwriteDependency$]).pipe((0,bw_external_rxjs_namespaceObject.concatMap)((_a) => bw_buffered_state_awaiter(this, [_a], void 0, function* ([hasValue, [shouldOverwrite, dependency]]) {
            if (hasValue && shouldOverwrite) {
                yield this.overwriteOutput(dependency);
            }
            return [false, null];
        })));
        // drive overwrites only when there's a subscription;
        // the output state determines when emissions occur
        const output$ = this.output.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((output) => [true, output]));
        this.state$ = (0,bw_external_rxjs_namespaceObject.merge)(overwrite$, output$).pipe((0,bw_external_rxjs_namespaceObject.filter)(([emit]) => emit), (0,bw_external_rxjs_namespaceObject.map)(([, output]) => output));
        this.combinedState$ = this.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => [this.output.userId, state]));
        this.bufferedState$ = this.bufferedState.state$;
    }
    overwriteOutput(dependency) {
        return bw_buffered_state_awaiter(this, void 0, void 0, function* () {
            // take the latest value from the buffer
            let buffered;
            yield this.bufferedState.update((state) => {
                buffered = state !== null && state !== void 0 ? state : null;
                return null;
            });
            // update the output state
            const isValid = yield this.key.isValid(buffered, dependency);
            if (isValid) {
                const output = yield this.key.map(buffered, dependency);
                yield this.output.update(() => output);
            }
        });
    }
    /** {@link SingleUserState.userId} */
    get userId() {
        return this.output.userId;
    }
    /** Buffers a value state. The buffered state overwrites the output
     *  state when a subscription occurs.
     *  @param value the state to roll over. Setting this to `null` or `undefined`
     *  has no effect.
     */
    buffer(value) {
        return bw_buffered_state_awaiter(this, void 0, void 0, function* () {
            const normalized = value !== null && value !== void 0 ? value : null;
            if (normalized !== null) {
                yield this.bufferedState.update(() => normalized);
            }
        });
    }
    /** Updates the output state.
     *  @param configureState a callback that returns an updated output
     *   state. The callback receives the state's present value as its
     *   first argument and the dependencies listed in `options.combinedLatestWith`
     *   as its second argument.
     *  @param options configures how the update is applied. See {@link StateUpdateOptions}.
     */
    update(configureState, options = null) {
        return this.output.update(configureState, options);
    }
}

;// ../../libs/common/src/tools/state/data-packer.abstraction.ts
/** A packing strategy that packs data into a string.
 */
class bw_DataPacker {
}

;// ../../libs/common/src/tools/state/padded-data-packer.ts


const bw_DATA_PACKING = Object.freeze({
    /** The character to use for padding. */
    padding: "0",
    /** The character dividing packed data. */
    divider: "|",
    /** A regular expression for detecting invalid padding. When the character
     *  changes, this should be updated to include the new padding pattern.
     */
    hasInvalidPadding: /[^0]/,
});
/** A packing strategy that conceals the length of secret data by padding it
 *  to a multiple of the frame size.
 *  @example
 *  // packed === "24|e2Zvbzp0cnVlfQ==|0000"
 *  const packer = new SecretPacker(24);
 *  const packed = packer.pack({ foo: true });
 */
class bw_PaddedDataPacker extends bw_DataPacker {
    /** Instantiates the padded data packer
     *  @param frameSize The size of the dataframe used to pad encrypted values.
     */
    constructor(frameSize) {
        super();
        this.frameSize = frameSize;
    }
    /**
     * Packs value into a string format that conceals the length by obscuring it
     * with the frameSize.
     * @see {@link DataPackerAbstraction.unpack}
     */
    pack(value) {
        // encode the value
        const json = JSON.stringify(value);
        const b64 = bw_utils_Utils.fromUtf8ToB64(json);
        // calculate packing metadata
        const frameSize = JSON.stringify(this.frameSize);
        const separatorLength = 2 * bw_DATA_PACKING.divider.length; // there are 2 separators
        const payloadLength = b64.length + frameSize.length + separatorLength;
        const paddingLength = this.frameSize - (payloadLength % this.frameSize);
        // pack the data, thereby concealing its length
        const padding = bw_DATA_PACKING.padding.repeat(paddingLength);
        const packed = `${frameSize}|${b64}|${padding}`;
        return packed;
    }
    /** {@link DataPackerAbstraction.unpack} */
    unpack(secret) {
        // frame size is stored before the JSON payload in base 10
        const frameEndIndex = secret.indexOf(bw_DATA_PACKING.divider);
        if (frameEndIndex < 1) {
            throw new Error("missing frame size");
        }
        const frameSize = parseInt(secret.slice(0, frameEndIndex), 10);
        const dataStartIndex = frameEndIndex + 1;
        // The decrypted string should be a multiple of the frame length
        if (secret.length % frameSize > 0) {
            throw new Error("invalid length");
        }
        // encoded data terminates with the divider, followed by the padding character
        const dataEndIndex = secret.lastIndexOf(bw_DATA_PACKING.divider);
        if (dataEndIndex == frameEndIndex) {
            throw new Error("missing json object");
        }
        const paddingStartIndex = dataEndIndex + 1;
        // If the padding contains invalid padding characters then the padding could be used
        // as a side channel for arbitrary data.
        if (secret.slice(paddingStartIndex).match(bw_DATA_PACKING.hasInvalidPadding)) {
            throw new Error("invalid padding");
        }
        // remove frame size and padding
        const b64 = secret.slice(dataStartIndex, dataEndIndex);
        // unpack the stored data
        const json = bw_utils_Utils.fromB64ToUtf8(b64);
        const unpacked = JSON.parse(json);
        return unpacked;
    }
}

;// ../../libs/common/src/tools/state/secret-key-definition.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/** Encryption and storage settings for data stored by a `SecretState`.
 */
class bw_SecretKeyDefinition {
    constructor(stateDefinition, key, classifier, options, 
    // type erasure is necessary here because typescript doesn't support
    // higher kinded types that generalize over collections. The invariants
    // needed to make this typesafe are maintained by the static factories.
    deconstruct, reconstruct) {
        this.stateDefinition = stateDefinition;
        this.key = key;
        this.classifier = classifier;
        this.options = options;
        this.deconstruct = deconstruct;
        this.reconstruct = reconstruct;
    }
    /** Converts the secret key to the `KeyDefinition` used for secret storage. */
    toEncryptedStateKey() {
        const secretKey = new bw_UserKeyDefinition(this.stateDefinition, this.key, {
            cleanupDelayMs: this.options.cleanupDelayMs,
            deserializer: (jsonValue) => jsonValue,
            // Clear encrypted state on logout
            clearOn: this.options.clearOn,
        });
        return secretKey;
    }
    /**
     * Define a secret state for a single value
     * @param stateDefinition The domain of the secret's durable state.
     * @param key Domain key that identifies the stored value. This key must not be reused
     *    in any capacity.
     * @param classifier Partitions the value into encrypted, discarded, and public data.
     * @param options Configures the operation of the secret state.
     */
    static value(stateDefinition, key, classifier, options) {
        return new bw_SecretKeyDefinition(stateDefinition, key, classifier, options, (value) => [[null, value]], ([[, inner]]) => inner);
    }
    /**
     * Define a secret state for an array of values. Each item is encrypted separately.
     * @param stateDefinition The domain of the secret's durable state.
     * @param key Domain key that identifies the stored items. This key must not be reused
     *    in any capacity.
     * @param classifier Partitions each item into encrypted, discarded, and public data.
     * @param options Configures the operation of the secret state.
     */
    static array(stateDefinition, key, classifier, options) {
        return new bw_SecretKeyDefinition(stateDefinition, key, classifier, options, (value) => value.map((v, id) => [id, v]), (values) => values.map(([, v]) => v));
    }
    /**
     * Define a secret state for a record. Each property is encrypted separately.
     * @param stateDefinition The domain of the secret's durable state.
     * @param key Domain key that identifies the stored properties. This key must not be reused
     *    in any capacity.
     * @param classifier Partitions each property into encrypted, discarded, and public data.
     * @param options Configures the operation of the secret state.
     */
    static record(stateDefinition, key, classifier, options) {
        return new bw_SecretKeyDefinition(stateDefinition, key, classifier, options, (value) => Object.entries(value), (values) => Object.fromEntries(values));
    }
}

;// ../../libs/common/src/tools/state/secret-state.ts
var bw_secret_state_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


const bw_ONE_MINUTE = 1000 * 60;
/** Stores account-specific secrets protected by a UserKeyEncryptor.
 *
 *  @remarks This state store changes the structure of `Plaintext` during
 *  storage, and requires user keys to operate. It is incompatible with sync,
 *  which expects the disk storage format to be identical to the sync format.
 *
 *  DO NOT USE THIS for synchronized data.
 */
class bw_SecretState {
    // The constructor is private to avoid creating a circular dependency when
    // wiring the derived and secret states together.
    constructor(key, $encryptor, userId, provider) {
        this.key = key;
        this.$encryptor = $encryptor;
        // construct the backing store
        this.encryptedState = provider.getUser(userId, key.toEncryptedStateKey());
        // cache plaintext
        this.combinedState$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([this.encryptedState.combinedState$, this.$encryptor]).pipe((0,bw_external_rxjs_namespaceObject.concatMap)((_a) => bw_secret_state_awaiter(this, [_a], void 0, function* ([[userId, state], encryptor]) { return [userId, yield this.declassifyAll(encryptor, state)]; })), (0,bw_external_rxjs_namespaceObject.share)({
            connector: () => {
                return new bw_external_rxjs_namespaceObject.ReplaySubject(1);
            },
            resetOnRefCountZero: () => { var _a; return (0,bw_external_rxjs_namespaceObject.timer)((_a = key.options.cleanupDelayMs) !== null && _a !== void 0 ? _a : bw_ONE_MINUTE); },
        }));
        this.state$ = this.combinedState$.pipe((0,bw_external_rxjs_namespaceObject.map)(([, state]) => state));
    }
    /** {@link SingleUserState.userId} */
    get userId() {
        return this.encryptedState.userId;
    }
    /** Creates a secret state bound to an account encryptor. The account must be unlocked
     *  when this method is called.
     *  @param userId: the user to which the secret state is bound.
     *  @param key Converts between a declassified secret and its formal type.
     *  @param provider constructs state objects.
     *  @param encryptor protects `Secret` data.
     *  @throws when `key.stateDefinition` is backed by memory storage.
     *  @remarks Secrets are written to a secret store as a named tuple. Data classification is
     *    determined by the encryptor's classifier. Secret-classification data is jsonified,
     *    encrypted, and stored in a `secret` property. Disclosed-classification data is stored
     *    in a `disclosed` property. Omitted-classification data is not stored.
     */
    static from(userId, key, provider, encryptor$) {
        const secretState = new bw_SecretState(key, encryptor$, userId, provider);
        return secretState;
    }
    declassifyItem(encryptor_1, _a) {
        return bw_secret_state_awaiter(this, arguments, void 0, function* (encryptor, { id, secret, disclosed }) {
            const encrypted = bw_enc_string_EncString.fromJSON(secret);
            const decrypted = yield encryptor.decrypt(encrypted);
            const declassified = this.key.classifier.declassify(disclosed, decrypted);
            const result = [id, this.key.options.deserializer(declassified)];
            return result;
        });
    }
    declassifyAll(encryptor, data) {
        return bw_secret_state_awaiter(this, void 0, void 0, function* () {
            // fail fast if there's no value
            if (data === null || data === undefined) {
                return null;
            }
            // decrypt each item
            const decryptTasks = data.map((item) => bw_secret_state_awaiter(this, void 0, void 0, function* () { return this.declassifyItem(encryptor, item); }));
            // reconstruct expected type
            const results = yield Promise.all(decryptTasks);
            const result = this.key.reconstruct(results);
            return result;
        });
    }
    classifyItem(encryptor_1, _a) {
        return bw_secret_state_awaiter(this, arguments, void 0, function* (encryptor, [id, item]) {
            const classified = this.key.classifier.classify(item);
            const encrypted = yield encryptor.encrypt(classified.secret);
            // the deserializer in the plaintextState's `derive` configuration always runs, but
            // `encryptedState` is not guaranteed to serialize the data, so it's necessary to
            // round-trip `encrypted` proactively.
            const serialized = {
                id,
                secret: JSON.parse(JSON.stringify(encrypted)),
                disclosed: classified.disclosed,
            };
            return serialized;
        });
    }
    classifyAll(encryptor, data) {
        return bw_secret_state_awaiter(this, void 0, void 0, function* () {
            // fail fast if there's no value
            if (data === null || data === undefined) {
                return null;
            }
            // convert the object to a list format so that all encrypt and decrypt
            // operations are self-similar
            const desconstructed = this.key.deconstruct(data);
            // encrypt each value individually
            const classifyTasks = desconstructed.map((item) => bw_secret_state_awaiter(this, void 0, void 0, function* () { return this.classifyItem(encryptor, item); }));
            const classified = yield Promise.all(classifyTasks);
            return classified;
        });
    }
    /** Updates the secret stored by this state.
     *  @param configureState a callback that returns an updated decrypted
     *   secret state. The callback receives the state's present value as its
     *   first argument and the dependencies listed in `options.combinedLatestWith`
     *   as its second argument.
     *  @param options configures how the update is applied. See {@link StateUpdateOptions}.
     *  @returns a promise that resolves with the updated value read from the state.
     *   The round-trip encrypts, decrypts, and deserializes the data, producing a new
     *   object.
     *  @remarks `configureState` must return a JSON-serializable object.
     *   If there are properties of your class which are not JSON-serializable,
     *   they can be lost when the secret state updates its backing store.
     */
    update(configureState_1) {
        return bw_secret_state_awaiter(this, arguments, void 0, function* (configureState, options = null) {
            var _a, _b, _c;
            const combineLatestWith = (0,bw_external_rxjs_namespaceObject.combineLatest)([
                (_a = options === null || options === void 0 ? void 0 : options.combineLatestWith) !== null && _a !== void 0 ? _a : (0,bw_external_rxjs_namespaceObject.of)(null),
                this.$encryptor,
            ]);
            // read the backing store
            let latestClassified;
            let latestCombined;
            let latestEncryptor;
            yield this.encryptedState.update((c) => c, {
                shouldUpdate: (latest, combined) => {
                    latestClassified = latest;
                    [latestCombined, latestEncryptor] = combined;
                    return false;
                },
                combineLatestWith,
            });
            // exit early if there's no update to apply
            const latestDeclassified = yield this.declassifyAll(latestEncryptor, latestClassified);
            const shouldUpdate = (_c = (_b = options === null || options === void 0 ? void 0 : options.shouldUpdate) === null || _b === void 0 ? void 0 : _b.call(options, latestDeclassified, latestCombined)) !== null && _c !== void 0 ? _c : true;
            if (!shouldUpdate) {
                return latestDeclassified;
            }
            // apply the update
            const updatedDeclassified = configureState(latestDeclassified, latestCombined);
            const updatedClassified = yield this.classifyAll(latestEncryptor, updatedDeclassified);
            yield this.encryptedState.update(() => updatedClassified);
            return updatedDeclassified;
        });
    }
}

;// ../../libs/tools/generator/core/src/abstractions/generator-strategy.abstraction.ts
/** Tailors the generator service to generate a specific kind of credentials */
class bw_GeneratorStrategy {
}

;// ../../libs/tools/generator/core/src/engine/rpc/create-forwarding-address.ts
class bw_create_forwarding_address_CreateForwardingAddressRpc {
    constructor(requestor, context) {
        this.requestor = requestor;
        this.context = context;
    }
    get createForwardingEmail() {
        return this.requestor.forwarder.createForwardingEmail;
    }
    toRequest(req) {
        const url = this.createForwardingEmail.url(req, this.context);
        const token = this.requestor.authenticate(req, this.context);
        const body = this.body(req);
        const request = new Request(url, {
            redirect: "manual",
            cache: "no-store",
            method: "POST",
            headers: new Headers(Object.assign(Object.assign({}, token), { "Content-Type": "application/json", Accept: "application/json" })),
            body,
        });
        return request;
    }
    body(req) {
        const toBody = this.createForwardingEmail.body;
        if (!toBody) {
            return undefined;
        }
        const body = toBody(req, this.context);
        if (!body) {
            return undefined;
        }
        return JSON.stringify(body);
    }
    hasJsonPayload(response) {
        return this.createForwardingEmail.hasJsonPayload(response, this.context);
    }
    processJson(json) {
        return this.createForwardingEmail.processJson(json, this.context);
    }
}

;// ../../libs/tools/generator/core/src/engine/rpc/get-account-id.ts
class bw_get_account_id_GetAccountIdRpc {
    constructor(requestor, context) {
        this.requestor = requestor;
        this.context = context;
    }
    hasJsonPayload(response) {
        return this.requestor.forwarder.getAccountId.hasJsonPayload(response, this.context);
    }
    processJson(json) {
        return this.requestor.forwarder.getAccountId.processJson(json, this.context);
    }
    toRequest(req) {
        const url = this.requestor.forwarder.getAccountId.url(req, this.context);
        const token = this.requestor.authenticate(req, this.context);
        const request = new Request(url, {
            redirect: "manual",
            cache: "no-store",
            method: "GET",
            headers: new Headers(Object.assign(Object.assign({}, token), { "Content-Type": "application/json", Accept: "application/json" })),
        });
        return request;
    }
}

;// ../../libs/tools/generator/core/src/strategies/options-classifier.ts
/** Classifies an object by excluding IntegrationRequest parameters.
 */
class bw_OptionsClassifier {
    /** Partitions `secret` into its disclosed properties and secret properties.
     *  @param value The object to partition
     *  @returns an object that classifies secrets.
     *    The `disclosed` member is new and contains disclosed properties.
     *    The `secret` member is a copy of the secret parameter, including its
     *    prototype, with all disclosed and excluded properties deleted.
     */
    classify(value) {
        const secret = JSON.parse(JSON.stringify(value));
        delete secret.website;
        const disclosed = {};
        return { disclosed, secret };
    }
    /** Merges the properties of `secret` and `disclosed`. When `secret` and
     *  `disclosed` contain the same property, the `secret` property overrides
     *  the `disclosed` property.
     *  @param disclosed an object whose disclosed properties are merged into
     *    the output. Unknown properties are ignored.
     *  @param secret an objects whose properties are merged into the output.
     *    Excluded properties are ignored. Unknown properties are retained.
     *  @returns a new object containing the merged data.
     *
     *  @remarks Declassified data is always jsonified--the purpose of classifying it is
     *   to Jsonify it,
     *   which causes type conversions.
     */
    declassify(_disclosed, secret) {
        const result = Object.assign(Object.assign({}, secret), { website: null });
        return result;
    }
}

;// ../../libs/tools/generator/core/src/strategies/forwarder-generator-strategy.ts
var bw_forwarder_generator_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore














const bw_OPTIONS_FRAME_SIZE = 512;
/** An email forwarding service configurable through an API. */
class bw_ForwarderGeneratorStrategy extends bw_GeneratorStrategy {
    /** Initializes the generator strategy
     *  @param encryptService protects sensitive forwarder options
     *  @param keyService looks up the user key when protecting data.
     *  @param stateProvider creates the durable state for options storage
     */
    constructor(configuration, client, i18nService, encryptService, keyService, stateProvider) {
        super();
        this.configuration = configuration;
        this.client = client;
        this.i18nService = i18nService;
        this.encryptService = encryptService;
        this.keyService = keyService;
        this.stateProvider = stateProvider;
        // configuration
        this.policy = bw_policy_type_enum_PolicyType.PasswordGenerator;
        this.defaults$ = bw_observe$PerUserId(() => this.configuration.forwarder.defaultSettings);
        this.toEvaluator = bw_newDefaultEvaluator();
        this.durableState = bw_sharedByUserId((userId) => this.getUserSecrets(userId));
        this.generate = (options) => bw_forwarder_generator_strategy_awaiter(this, void 0, void 0, function* () {
            const requestOptions = { website: options.website };
            const getAccount = yield this.getAccountId(this.configuration, options);
            if (getAccount) {
                requestOptions.accountId = yield this.client.fetchJson(getAccount, requestOptions);
            }
            const create = this.createForwardingAddress(this.configuration, options);
            const result = yield this.client.fetchJson(create, requestOptions);
            return result;
        });
    }
    get key() {
        return this.configuration.forwarder.settings;
    }
    get rolloverKey() {
        return this.configuration.forwarder.importBuffer;
    }
    // per-user encrypted state
    getUserSecrets(userId) {
        // construct the encryptor
        const packer = new bw_PaddedDataPacker(bw_OPTIONS_FRAME_SIZE);
        const encryptor$ = this.keyService.userKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((key) => (key ? new bw_UserKeyEncryptor(userId, this.encryptService, key, packer) : null)), (0,bw_external_rxjs_namespaceObject.filter)((encryptor) => !!encryptor));
        // always exclude request properties
        const classifier = new bw_OptionsClassifier();
        // Derive the secret key definition
        const key = bw_SecretKeyDefinition.value(this.key.stateDefinition, this.key.key, classifier, {
            deserializer: (d) => this.key.deserializer(d),
            cleanupDelayMs: this.key.cleanupDelayMs,
            clearOn: this.key.clearOn,
        });
        // the type parameter is explicit because type inference fails for `Omit<Options, "website">`
        const secretState = bw_SecretState.from(userId, key, this.stateProvider, encryptor$);
        // rollover should occur once the user key is available for decryption
        const canDecrypt$ = this.keyService.userKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((key) => key !== null));
        const rolloverState = new bw_BufferedState(this.stateProvider, this.rolloverKey, secretState, canDecrypt$);
        // cast through unknown required because there's no way to prove to
        // the compiler that `OptionsClassifier` runs within the buffer wrapping
        // the secret state.
        return rolloverState;
    }
    createContext(configuration, settings) {
        return new bw_forwarder_context_ForwarderContext(configuration, settings, this.i18nService);
    }
    createForwardingAddress(configuration, settings) {
        const context = this.createContext(configuration, settings);
        const rpc = new bw_create_forwarding_address_CreateForwardingAddressRpc(configuration, context);
        return rpc;
    }
    getAccountId(configuration, settings) {
        if (!configuration.forwarder.getAccountId) {
            return null;
        }
        const context = this.createContext(configuration, settings);
        const rpc = new bw_get_account_id_GetAccountIdRpc(configuration, context);
        return rpc;
    }
}

;// ../../libs/tools/generator/core/src/strategies/storage.ts

/** plaintext password generation options */
const bw_PASSWORD_SETTINGS = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "passwordGeneratorSettings", {
    deserializer: (value) => value,
    clearOn: [],
});
/** plaintext passphrase generation options */
const bw_PASSPHRASE_SETTINGS = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "passphraseGeneratorSettings", {
    deserializer: (value) => value,
    clearOn: [],
});
/** plaintext username generation options */
const bw_EFF_USERNAME_SETTINGS = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "effUsernameGeneratorSettings", {
    deserializer: (value) => value,
    clearOn: [],
});
/** plaintext configuration for a domain catch-all address. */
const bw_CATCHALL_SETTINGS = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "catchallGeneratorSettings", {
    deserializer: (value) => value,
    clearOn: [],
});
/** plaintext configuration for an email subaddress. */
const bw_SUBADDRESS_SETTINGS = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "subaddressGeneratorSettings", {
    deserializer: (value) => value,
    clearOn: [],
});

;// ../../libs/tools/generator/core/src/strategies/passphrase-generator-strategy.ts
var bw_passphrase_generator_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





/** Generates passphrases composed of random words */
class bw_PassphraseGeneratorStrategy {
    /** instantiates the password generator strategy.
     *  @param legacy generates the passphrase
     *  @param stateProvider provides durable state
     */
    constructor(randomizer, stateProvider) {
        this.randomizer = randomizer;
        this.stateProvider = stateProvider;
        // configuration
        this.durableState = bw_sharedStateByUserId(bw_PASSPHRASE_SETTINGS, this.stateProvider);
        this.defaults$ = bw_observe$PerUserId(() => bw_DefaultPassphraseGenerationOptions);
        this.policy = bw_policy_type_enum_PolicyType.PasswordGenerator;
    }
    toEvaluator() {
        return bw_mapPolicyToEvaluator(bw_Policies.Passphrase);
    }
    // algorithm
    generate(options) {
        return bw_passphrase_generator_strategy_awaiter(this, void 0, void 0, function* () {
            const request = bw_optionsToEffWordListRequest(options);
            return this.randomizer.randomEffLongWords(request);
        });
    }
}

;// ../../libs/tools/generator/core/src/strategies/password-generator-strategy.ts
var bw_password_generator_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





/** Generates passwords composed of random characters */
class bw_PasswordGeneratorStrategy {
    /** instantiates the password generator strategy.
     *  @param legacy generates the password
     */
    constructor(randomizer, stateProvider) {
        this.randomizer = randomizer;
        this.stateProvider = stateProvider;
        // configuration
        this.durableState = bw_sharedStateByUserId(bw_PASSWORD_SETTINGS, this.stateProvider);
        this.defaults$ = bw_observe$PerUserId(() => bw_DefaultPasswordGenerationOptions);
        this.policy = bw_policy_type_enum_PolicyType.PasswordGenerator;
    }
    toEvaluator() {
        return bw_mapPolicyToEvaluator(bw_Policies.Password);
    }
    // algorithm
    generate(options) {
        return bw_password_generator_strategy_awaiter(this, void 0, void 0, function* () {
            const request = bw_optionsToRandomAsciiRequest(options);
            const result = yield this.randomizer.randomAscii(request);
            return result;
        });
    }
}

;// ../../libs/tools/generator/core/src/strategies/catchall-generator-strategy.ts
var bw_catchall_generator_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





/** Strategy for creating usernames using a catchall email address */
class bw_CatchallGeneratorStrategy {
    /** Instantiates the generation strategy
     *  @param usernameService generates a catchall address for a domain
     */
    constructor(emailCalculator, emailRandomizer, stateProvider, defaultOptions = bw_DefaultCatchallOptions) {
        this.emailCalculator = emailCalculator;
        this.emailRandomizer = emailRandomizer;
        this.stateProvider = stateProvider;
        this.defaultOptions = defaultOptions;
        // configuration
        this.durableState = bw_sharedStateByUserId(bw_CATCHALL_SETTINGS, this.stateProvider);
        this.defaults$ = bw_observe$PerUserId(() => this.defaultOptions);
        this.toEvaluator = bw_newDefaultEvaluator();
        this.policy = bw_policy_type_enum_PolicyType.PasswordGenerator;
    }
    // algorithm
    generate(options) {
        return bw_catchall_generator_strategy_awaiter(this, void 0, void 0, function* () {
            if (options.catchallType == null) {
                options.catchallType = "random";
            }
            if (options.catchallType === "website-name") {
                return yield this.emailCalculator.concatenate(options.website, options.catchallDomain);
            }
            return this.emailRandomizer.randomAsciiCatchall(options.catchallDomain);
        });
    }
}

;// ../../libs/tools/generator/core/src/strategies/subaddress-generator-strategy.ts
var bw_subaddress_generator_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





/** Strategy for creating an email subaddress
 *  @remarks The subaddress is the part following the `+`.
 *  For example, if the email address is `jd+xyz@domain.io`,
 *  the subaddress is `xyz`.
 */
class bw_SubaddressGeneratorStrategy {
    /** Instantiates the generation strategy
     *  @param usernameService generates an email subaddress from an email address
     */
    constructor(emailCalculator, emailRandomizer, stateProvider, defaultOptions = bw_DefaultSubaddressOptions) {
        this.emailCalculator = emailCalculator;
        this.emailRandomizer = emailRandomizer;
        this.stateProvider = stateProvider;
        this.defaultOptions = defaultOptions;
        // configuration
        this.durableState = bw_sharedStateByUserId(bw_SUBADDRESS_SETTINGS, this.stateProvider);
        this.defaults$ = bw_observe$PerUserId(() => this.defaultOptions);
        this.toEvaluator = bw_newDefaultEvaluator();
        this.policy = bw_policy_type_enum_PolicyType.PasswordGenerator;
    }
    // algorithm
    generate(options) {
        return bw_subaddress_generator_strategy_awaiter(this, void 0, void 0, function* () {
            if (options.subaddressType == null) {
                options.subaddressType = "random";
            }
            if (options.subaddressType === "website-name") {
                return this.emailCalculator.appendToSubaddress(options.website, options.subaddressEmail);
            }
            return this.emailRandomizer.randomAsciiSubaddress(options.subaddressEmail);
        });
    }
}

;// ../../libs/tools/generator/core/src/strategies/eff-username-generator-strategy.ts
var bw_eff_username_generator_strategy_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





/** Strategy for creating usernames from the EFF wordlist */
class bw_EffUsernameGeneratorStrategy {
    /** Instantiates the generation strategy
     *  @param usernameService generates a username from EFF word list
     */
    constructor(randomizer, stateProvider, defaultOptions = bw_DefaultEffUsernameOptions) {
        this.randomizer = randomizer;
        this.stateProvider = stateProvider;
        this.defaultOptions = defaultOptions;
        // configuration
        this.durableState = bw_sharedStateByUserId(bw_EFF_USERNAME_SETTINGS, this.stateProvider);
        this.defaults$ = bw_observe$PerUserId(() => this.defaultOptions);
        this.toEvaluator = bw_newDefaultEvaluator();
        this.policy = bw_policy_type_enum_PolicyType.PasswordGenerator;
    }
    // algorithm
    generate(options) {
        return bw_eff_username_generator_strategy_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            const casing = ((_a = options.wordCapitalize) !== null && _a !== void 0 ? _a : bw_DefaultEffUsernameOptions.wordCapitalize)
                ? "TitleCase"
                : "lowercase";
            const digits = ((_b = options.wordIncludeNumber) !== null && _b !== void 0 ? _b : bw_DefaultEffUsernameOptions.wordIncludeNumber)
                ? bw_UsernameDigits.enabled
                : bw_UsernameDigits.disabled;
            const word = yield this.randomizer.randomWords({ numberOfWords: 1, casing, digits });
            return word;
        });
    }
}

;// ../../libs/tools/generator/core/src/strategies/index.ts







;// ../../libs/tools/generator/core/src/index.ts
// The root module interface has API stability guarantees





// These internal interfacess are exposed for use by other generator modules
// They are unstable and may change arbitrarily







;// ./src/tools/generate.command.ts
var bw_generate_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_GenerateCommand {
    constructor(passwordGenerationService, stateService) {
        this.passwordGenerationService = passwordGenerationService;
        this.stateService = stateService;
    }
    run(cmdOptions) {
        return bw_generate_command_awaiter(this, void 0, void 0, function* () {
            const normalizedOptions = new bw_generate_command_Options(cmdOptions);
            const options = {
                uppercase: normalizedOptions.uppercase,
                lowercase: normalizedOptions.lowercase,
                number: normalizedOptions.number,
                special: normalizedOptions.special,
                length: normalizedOptions.length,
                type: normalizedOptions.type,
                wordSeparator: normalizedOptions.separator,
                numWords: normalizedOptions.words,
                capitalize: normalizedOptions.capitalize,
                includeNumber: normalizedOptions.includeNumber,
                minNumber: normalizedOptions.minNumber,
                minSpecial: normalizedOptions.minSpecial,
                ambiguous: !normalizedOptions.ambiguous,
            };
            const enforcedOptions = (yield this.stateService.getIsAuthenticated())
                ? (yield this.passwordGenerationService.enforcePasswordGeneratorPoliciesOnOptions(options))[0]
                : options;
            const password = yield this.passwordGenerationService.generatePassword(enforcedOptions);
            const res = new bw_StringResponse(password);
            return bw_Response.success(res);
        });
    }
}
class bw_generate_command_Options {
    constructor(passedOptions) {
        this.uppercase = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.uppercase);
        this.lowercase = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.lowercase);
        this.number = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.number);
        this.special = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.special);
        this.capitalize = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.capitalize);
        this.includeNumber = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.includeNumber);
        this.ambiguous = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.ambiguous);
        this.length = bw_CliUtils.convertNumberOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.length, bw_DefaultPasswordGenerationOptions.length);
        this.type = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.passphrase) ? "passphrase" : "password";
        this.separator = bw_CliUtils.convertStringOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.separator, bw_DefaultPassphraseGenerationOptions.wordSeparator);
        this.words = bw_CliUtils.convertNumberOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.words, bw_DefaultPassphraseGenerationOptions.numWords);
        this.minNumber = bw_CliUtils.convertNumberOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.minNumber, bw_DefaultPasswordGenerationOptions.minNumber);
        this.minSpecial = bw_CliUtils.convertNumberOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.minSpecial, bw_DefaultPasswordGenerationOptions.minSpecial);
        if (!this.uppercase && !this.lowercase && !this.special && !this.number) {
            this.lowercase = true;
            this.uppercase = true;
            this.number = true;
        }
        if (this.length < 5) {
            this.length = 5;
        }
        if (this.words < 3) {
            this.words = 3;
        }
        if (this.separator === "space") {
            this.separator = " ";
        }
        else if (this.separator === "empty") {
            this.separator = "";
        }
        else if (this.separator != null && this.separator.length > 1) {
            this.separator = this.separator[0];
        }
    }
}

;// ./src/vault/sync.command.ts
var bw_sync_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_SyncCommand {
    constructor(syncService) {
        this.syncService = syncService;
    }
    run(cmdOptions) {
        return bw_sync_command_awaiter(this, void 0, void 0, function* () {
            const normalizedOptions = new bw_sync_command_Options(cmdOptions);
            if (normalizedOptions.last) {
                return yield this.getLastSync();
            }
            try {
                yield this.syncService.fullSync(normalizedOptions.force, true);
                const res = new bw_MessageResponse("Syncing complete.", null);
                return bw_Response.success(res);
            }
            catch (e) {
                const response = bw_Response.error(e);
                response.message = "Syncing failed: " + response.message;
                return response;
            }
        });
    }
    getLastSync() {
        return bw_sync_command_awaiter(this, void 0, void 0, function* () {
            const lastSyncDate = yield this.syncService.getLastSync();
            const res = new bw_StringResponse(lastSyncDate == null ? null : lastSyncDate.toISOString());
            return bw_Response.success(res);
        });
    }
}
class bw_sync_command_Options {
    constructor(passedOptions) {
        this.last = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.last);
        this.force = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.force);
    }
}

;// ./src/program.ts
var bw_program_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



















const bw_program_writeLn = bw_CliUtils.writeLn;
class bw_Program extends bw_BaseProgram {
    register() {
        return bw_program_awaiter(this, void 0, void 0, function* () {
            bw_external_commander_namespaceObject.program
                .option("--pretty", "Format output. JSON is tabbed with two spaces.")
                .option("--raw", "Return raw output instead of a descriptive message.")
                .option("--response", "Return a JSON formatted version of response output.")
                .option("--cleanexit", "Exit with a success exit code (0) unless an error is thrown.")
                .option("--quiet", "Don't return anything to stdout.")
                .option("--nointeraction", "Do not prompt for interactive user input.")
                .option("--session <session>", "Pass session key instead of reading from env.")
                .version(yield this.serviceContainer.platformUtilsService.getApplicationVersion(), "-v, --version");
            bw_external_commander_namespaceObject.program.on("option:pretty", () => {
                process.env.BW_PRETTY = "true";
            });
            bw_external_commander_namespaceObject.program.on("option:raw", () => {
                process.env.BW_RAW = "true";
            });
            bw_external_commander_namespaceObject.program.on("option:quiet", () => {
                process.env.BW_QUIET = "true";
            });
            bw_external_commander_namespaceObject.program.on("option:response", () => {
                process.env.BW_RESPONSE = "true";
            });
            bw_external_commander_namespaceObject.program.on("option:cleanexit", () => {
                process.env.BW_CLEANEXIT = "true";
            });
            bw_external_commander_namespaceObject.program.on("option:nointeraction", () => {
                process.env.BW_NOINTERACTION = "true";
            });
            bw_external_commander_namespaceObject.program.on("option:session", (key) => {
                process.env.BW_SESSION = key;
            });
            bw_external_commander_namespaceObject.program.on("command:*", () => {
                bw_program_writeLn(bw_external_chalk_namespaceObject.redBright("Invalid command: " + bw_external_commander_namespaceObject.program.args.join(" ")), false, true);
                bw_program_writeLn("See --help for a list of available commands.", true, true);
                process.exitCode = 1;
            });
            bw_external_commander_namespaceObject.program.on("--help", () => {
                bw_program_writeLn(bw_external_chalk_namespaceObject.yellowBright("\n  Tip: Managing and retrieving secrets for dev environments is easier with Bitwarden Secrets Manager. Learn more under https://bitwarden.com/products/secrets-manager/"));
                bw_program_writeLn("\n  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw login");
                bw_program_writeLn("    bw lock");
                bw_program_writeLn("    bw unlock myPassword321");
                bw_program_writeLn("    bw list --help");
                bw_program_writeLn("    bw list items --search google");
                bw_program_writeLn("    bw get item 99ee88d2-6046-4ea7-92c2-acac464b1412");
                bw_program_writeLn("    bw get password google.com");
                bw_program_writeLn('    echo \'{"name":"My Folder"}\' | bw encode');
                bw_program_writeLn("    bw create folder eyJuYW1lIjoiTXkgRm9sZGVyIn0K");
                bw_program_writeLn("    bw edit folder c7c7b60b-9c61-40f2-8ccd-36c49595ed72 eyJuYW1lIjoiTXkgRm9sZGVyMiJ9Cg==");
                bw_program_writeLn("    bw delete item 99ee88d2-6046-4ea7-92c2-acac464b1412");
                bw_program_writeLn("    bw generate -lusn --length 18");
                bw_program_writeLn("    bw config server https://bitwarden.example.com");
                bw_program_writeLn("    bw send -f ./file.ext");
                bw_program_writeLn('    bw send "text to send"');
                bw_program_writeLn('    echo "text to send" | bw send');
                bw_program_writeLn("    bw receive https://vault.bitwarden.com/#/send/rg3iuoS_Akm2gqy6ADRHmg/Ht7dYjsqjmgqUM3rjzZDSQ");
                bw_program_writeLn("", true);
            });
            bw_external_commander_namespaceObject.program
                .command("sdk-version")
                .description("Print the SDK version.")
                .action(() => bw_program_awaiter(this, void 0, void 0, function* () {
                const sdkVersion = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.serviceContainer.sdkService.version$);
                bw_program_writeLn(sdkVersion, true);
            }));
            bw_external_commander_namespaceObject.program
                .command("login [email] [password]")
                .description("Log into a user account.")
                .option("--method <method>", "Two-step login method.")
                .option("--code <code>", "Two-step login code.")
                .option("--sso", "Log in with Single-Sign On.")
                .option("--apikey", "Log in with an Api Key.")
                .option("--passwordenv <passwordenv>", "Environment variable storing your password")
                .option("--passwordfile <passwordfile>", "Path to a file containing your password as its first line")
                .option("--check", "Check login status.", () => bw_program_awaiter(this, void 0, void 0, function* () {
                const authed = yield this.serviceContainer.stateService.getIsAuthenticated();
                if (authed) {
                    const res = new bw_MessageResponse("You are logged in!", null);
                    this.processResponse(bw_Response.success(res), true);
                }
                this.processResponse(bw_Response.error("You are not logged in."), true);
            }))
                .on("--help", () => {
                bw_program_writeLn("\n  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("    See docs for valid `method` enum values.");
                bw_program_writeLn("");
                bw_program_writeLn("    Pass `--raw` option to only return the session key.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw login");
                bw_program_writeLn("    bw login john@example.com myPassword321 --raw");
                bw_program_writeLn("    bw login john@example.com myPassword321 --method 1 --code 249213");
                bw_program_writeLn("    bw login --sso");
                bw_program_writeLn("", true);
            })
                .action((email, password, options) => bw_program_awaiter(this, void 0, void 0, function* () {
                if (!options.check) {
                    yield this.exitIfAuthed();
                    const command = new bw_LoginCommand(this.serviceContainer.loginStrategyService, this.serviceContainer.authService, this.serviceContainer.apiService, this.serviceContainer.masterPasswordApiService, this.serviceContainer.cryptoFunctionService, this.serviceContainer.environmentService, this.serviceContainer.passwordGenerationService, this.serviceContainer.passwordStrengthService, this.serviceContainer.platformUtilsService, this.serviceContainer.accountService, this.serviceContainer.keyService, this.serviceContainer.policyService, this.serviceContainer.twoFactorService, this.serviceContainer.syncService, this.serviceContainer.keyConnectorService, this.serviceContainer.policyApiService, this.serviceContainer.organizationService, () => bw_program_awaiter(this, void 0, void 0, function* () { return yield this.serviceContainer.logout(); }), this.serviceContainer.kdfConfigService, this.serviceContainer.ssoUrlService);
                    const response = yield command.run(email, password, options);
                    this.processResponse(response, true);
                }
            }));
            bw_external_commander_namespaceObject.program
                .command("logout")
                .description("Log out of the current user account.")
                .on("--help", () => {
                bw_program_writeLn("\n  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw logout");
                bw_program_writeLn("", true);
            })
                .action((cmd) => bw_program_awaiter(this, void 0, void 0, function* () {
                yield this.exitIfNotAuthed();
                const command = new bw_LogoutCommand(this.serviceContainer.authService, this.serviceContainer.i18nService, () => bw_program_awaiter(this, void 0, void 0, function* () { return yield this.serviceContainer.logout(); }));
                const response = yield command.run();
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("lock")
                .description("Lock the vault and destroy active session keys.")
                .on("--help", () => {
                bw_program_writeLn("\n  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw lock");
                bw_program_writeLn("", true);
            })
                .action((cmd) => bw_program_awaiter(this, void 0, void 0, function* () {
                const userId = yield this.exitIfNotAuthed();
                if (yield this.serviceContainer.keyConnectorService.getUsesKeyConnector(userId)) {
                    const logoutCommand = new bw_LogoutCommand(this.serviceContainer.authService, this.serviceContainer.i18nService, () => bw_program_awaiter(this, void 0, void 0, function* () { return yield this.serviceContainer.logout(); }));
                    yield logoutCommand.run();
                    this.processResponse(bw_Response.error("You cannot lock your vault because you are using Key Connector. " +
                        "To protect your vault, you have been logged out."), true);
                    return;
                }
                const command = new bw_LockCommand(this.serviceContainer.vaultTimeoutService);
                const response = yield command.run();
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("unlock [password]")
                .description("Unlock the vault and return a new session key.")
                .on("--help", () => {
                bw_program_writeLn("\n  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("    After unlocking, any previous session keys will no longer be valid.");
                bw_program_writeLn("");
                bw_program_writeLn("    Pass `--raw` option to only return the session key.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw unlock");
                bw_program_writeLn("    bw unlock myPassword321");
                bw_program_writeLn("    bw unlock myPassword321 --raw");
                bw_program_writeLn("", true);
            })
                .option("--check", "Check lock status.", () => bw_program_awaiter(this, void 0, void 0, function* () {
                yield this.exitIfNotAuthed();
                const authStatus = yield this.serviceContainer.authService.getAuthStatus();
                if (authStatus === bw_authentication_status_AuthenticationStatus.Unlocked) {
                    const res = new bw_MessageResponse("Vault is unlocked!", null);
                    this.processResponse(bw_Response.success(res), true);
                }
                else {
                    this.processResponse(bw_Response.error("Vault is locked."), true);
                }
            }))
                .option("--passwordenv <passwordenv>", "Environment variable storing your password")
                .option("--passwordfile <passwordfile>", "Path to a file containing your password as its first line")
                .action((password, cmd) => bw_program_awaiter(this, void 0, void 0, function* () {
                if (!cmd.check) {
                    yield this.exitIfNotAuthed();
                    const command = new bw_UnlockCommand(this.serviceContainer.accountService, this.serviceContainer.masterPasswordService, this.serviceContainer.keyService, this.serviceContainer.userVerificationService, this.serviceContainer.cryptoFunctionService, this.serviceContainer.logService, this.serviceContainer.keyConnectorService, this.serviceContainer.environmentService, this.serviceContainer.syncService, this.serviceContainer.organizationApiService, () => bw_program_awaiter(this, void 0, void 0, function* () { return yield this.serviceContainer.logout(); }));
                    const response = yield command.run(password, cmd);
                    this.processResponse(response);
                }
            }));
            bw_external_commander_namespaceObject.program
                .command("sync")
                .description("Pull the latest vault data from server.")
                .option("-f, --force", "Force a full sync.")
                .option("--last", "Get the last sync date.")
                .on("--help", () => {
                bw_program_writeLn("\n  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw sync");
                bw_program_writeLn("    bw sync -f");
                bw_program_writeLn("    bw sync --last");
                bw_program_writeLn("", true);
            })
                .action((cmd) => bw_program_awaiter(this, void 0, void 0, function* () {
                yield this.exitIfNotAuthed();
                const command = new bw_SyncCommand(this.serviceContainer.syncService);
                const response = yield command.run(cmd);
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("generate")
                .description("Generate a password/passphrase.")
                .option("-u, --uppercase", "Include uppercase characters.")
                .option("-l, --lowercase", "Include lowercase characters.")
                .option("-n, --number", "Include numeric characters.")
                .option("-s, --special", "Include special characters.")
                .option("-p, --passphrase", "Generate a passphrase.")
                .option("--length <length>", "Length of the password.")
                .option("--words <words>", "Number of words.")
                .option("--minNumber <count>", "Minimum number of numeric characters.")
                .option("--minSpecial <count>", "Minimum number of special characters.")
                .option("--separator <separator>", "Word separator.")
                .option("-c, --capitalize", "Title case passphrase.")
                .option("--includeNumber", "Passphrase includes number.")
                .option("--ambiguous", "Avoid ambiguous characters.")
                .on("--help", () => {
                bw_program_writeLn("\n  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("    Default options are `-uln --length 14`.");
                bw_program_writeLn("");
                bw_program_writeLn("    Minimum `length` is 5.");
                bw_program_writeLn("");
                bw_program_writeLn("    Minimum `words` is 3.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw generate");
                bw_program_writeLn("    bw generate -u -l --length 18");
                bw_program_writeLn("    bw generate -ulns --length 25");
                bw_program_writeLn("    bw generate -ul");
                bw_program_writeLn("    bw generate -p --separator _");
                bw_program_writeLn("    bw generate -p --words 5 --separator space");
                bw_program_writeLn("    bw generate -p --words 5 --separator empty");
                bw_program_writeLn("", true);
            })
                .action((options) => bw_program_awaiter(this, void 0, void 0, function* () {
                const command = new bw_GenerateCommand(this.serviceContainer.passwordGenerationService, this.serviceContainer.stateService);
                const response = yield command.run(options);
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("encode")
                .description("Base 64 encode stdin.")
                .on("--help", () => {
                bw_program_writeLn("\n  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("    Use to create `encodedJson` for `create` and `edit` commands.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn('    echo \'{"name":"My Folder"}\' | bw encode');
                bw_program_writeLn("", true);
            })
                .action(() => bw_program_awaiter(this, void 0, void 0, function* () {
                const command = new bw_EncodeCommand();
                const response = yield command.run();
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("config <setting> [value]")
                .description("Configure CLI settings.")
                .option("--web-vault <url>", "Provides a custom web vault URL that differs from the base URL.")
                .option("--api <url>", "Provides a custom API URL that differs from the base URL.")
                .option("--identity <url>", "Provides a custom identity URL that differs from the base URL.")
                .option("--icons <url>", "Provides a custom icons service URL that differs from the base URL.")
                .option("--notifications <url>", "Provides a custom notifications URL that differs from the base URL.")
                .option("--events <url>", "Provides a custom events URL that differs from the base URL.")
                .option("--key-connector <url>", "Provides the URL for your Key Connector server.")
                .on("--help", () => {
                bw_program_writeLn("\n  Settings:");
                bw_program_writeLn("");
                bw_program_writeLn("    server - On-premises hosted installation URL.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw config server");
                bw_program_writeLn("    bw config server https://bw.company.com");
                bw_program_writeLn("    bw config server bitwarden.com");
                bw_program_writeLn("    bw config server --api http://localhost:4000 --identity http://localhost:33656");
                bw_program_writeLn("", true);
            })
                .action((setting, value, options) => bw_program_awaiter(this, void 0, void 0, function* () {
                const command = new bw_ConfigCommand(this.serviceContainer.environmentService, this.serviceContainer.accountService);
                const response = yield command.run(setting, value, options);
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("update")
                .description("Check for updates.")
                .on("--help", () => {
                bw_program_writeLn("\n  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("    Returns the URL to download the newest version of this CLI tool.");
                bw_program_writeLn("");
                bw_program_writeLn("    Use the `--raw` option to return only the download URL for the update.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw update");
                bw_program_writeLn("    bw update --raw");
                bw_program_writeLn("", true);
            })
                .action(() => bw_program_awaiter(this, void 0, void 0, function* () {
                const command = new bw_UpdateCommand(this.serviceContainer.platformUtilsService, this.serviceContainer.apiService);
                const response = yield command.run();
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("completion")
                .description("Generate shell completions.")
                .option("--shell <shell>", "Shell to generate completions for.")
                .on("--help", () => {
                bw_program_writeLn("\n  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("    Valid shells are `zsh`.");
                bw_program_writeLn("");
                bw_program_writeLn("  Examples:");
                bw_program_writeLn("");
                bw_program_writeLn("    bw completion --shell zsh");
                bw_program_writeLn("", true);
            })
                .action((options, cmd) => bw_program_awaiter(this, void 0, void 0, function* () {
                const command = new bw_CompletionCommand();
                const response = yield command.run(options);
                this.processResponse(response);
            }));
            bw_external_commander_namespaceObject.program
                .command("status")
                .description("Show server, last sync, user information, and vault status.")
                .on("--help", () => {
                bw_program_writeLn("");
                bw_program_writeLn("");
                bw_program_writeLn("  Example return value:");
                bw_program_writeLn("");
                bw_program_writeLn("    {");
                bw_program_writeLn('      "serverUrl": "https://bitwarden.example.com",');
                bw_program_writeLn('      "lastSync": "2020-06-16T06:33:51.419Z",');
                bw_program_writeLn('      "userEmail": "user@example.com,');
                bw_program_writeLn('      "userId": "00000000-0000-0000-0000-000000000000",');
                bw_program_writeLn('      "status": "locked"');
                bw_program_writeLn("    }");
                bw_program_writeLn("");
                bw_program_writeLn("  Notes:");
                bw_program_writeLn("");
                bw_program_writeLn("  `status` is one of:");
                bw_program_writeLn("    - `unauthenticated` when you are not logged in");
                bw_program_writeLn("    - `locked` when you are logged in and the vault is locked");
                bw_program_writeLn("    - `unlocked` when you are logged in and the vault is unlocked");
                bw_program_writeLn("", true);
            })
                .action(() => bw_program_awaiter(this, void 0, void 0, function* () {
                const command = new bw_StatusCommand(this.serviceContainer.environmentService, this.serviceContainer.syncService, this.serviceContainer.accountService, this.serviceContainer.authService);
                const response = yield command.run();
                this.processResponse(response);
            }));
        });
    }
}

;// ../../libs/common/src/tools/send/enums/send-type.ts
var bw_SendType;
(function (SendType) {
    SendType[SendType["Text"] = 0] = "Text";
    SendType[SendType["File"] = 1] = "File";
})(bw_SendType || (bw_SendType = {}));

;// ../../libs/common/src/auth/abstractions/account.service.ts
function bw_accountInfoEqual(a, b) {
    if (a == null && b == null) {
        return true;
    }
    if (a == null || b == null) {
        return false;
    }
    const keys = new Set([...Object.keys(a), ...Object.keys(b)]);
    for (const key of keys) {
        if (a[key] !== b[key]) {
            return false;
        }
    }
    return true;
}
class bw_AccountService {
}
class bw_InternalAccountService extends (/* unused pure expression or super */ null && (bw_AccountService)) {
}

;// ../../libs/common/src/auth/services/account.service.ts
var bw_account_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




const bw_ACCOUNT_ACCOUNTS = bw_KeyDefinition.record(bw_ACCOUNT_DISK, "accounts", {
    deserializer: (accountInfo) => accountInfo,
});
const bw_ACCOUNT_ACTIVE_ACCOUNT_ID = new bw_KeyDefinition(bw_ACCOUNT_DISK, "activeAccountId", {
    deserializer: (id) => id,
});
const bw_ACCOUNT_ACTIVITY = bw_KeyDefinition.record(bw_ACCOUNT_DISK, "activity", {
    deserializer: (activity) => new Date(activity),
});
const bw_ACCOUNT_VERIFY_NEW_DEVICE_LOGIN = new bw_UserKeyDefinition(bw_ACCOUNT_DISK, "verifyNewDeviceLogin", {
    deserializer: (verifyDevices) => verifyDevices,
    clearOn: ["logout"],
});
const bw_LOGGED_OUT_INFO = {
    email: "",
    emailVerified: false,
    name: undefined,
};
/**
 * An rxjs map operator that extracts the UserId from an account, or throws if the account or UserId are null.
 */
const bw_getUserId = (0,bw_external_rxjs_namespaceObject.map)((account) => {
    if (account == null) {
        throw new Error("Null or undefined account");
    }
    return account.id;
});
/**
 * An rxjs map operator that extracts the UserId from an account, or returns undefined if the account or UserId are null.
 */
const bw_getOptionalUserId = (0,bw_external_rxjs_namespaceObject.map)((account) => { var _a; return (_a = account === null || account === void 0 ? void 0 : account.id) !== null && _a !== void 0 ? _a : null; });
class bw_AccountServiceImplementation {
    constructor(messagingService, logService, globalStateProvider, singleUserStateProvider) {
        this.messagingService = messagingService;
        this.logService = logService;
        this.globalStateProvider = globalStateProvider;
        this.singleUserStateProvider = singleUserStateProvider;
        this.accountsState = this.globalStateProvider.get(bw_ACCOUNT_ACCOUNTS);
        this.activeAccountIdState = this.globalStateProvider.get(bw_ACCOUNT_ACTIVE_ACCOUNT_ID);
        this.accounts$ = this.accountsState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((accounts) => (accounts == null ? {} : accounts)));
        this.activeAccount$ = this.activeAccountIdState.state$.pipe((0,bw_external_rxjs_namespaceObject.combineLatestWith)(this.accounts$), (0,bw_external_rxjs_namespaceObject.map)(([id, accounts]) => (id ? Object.assign({ id }, accounts[id]) : null)), (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)((a, b) => (a === null || a === void 0 ? void 0 : a.id) === (b === null || b === void 0 ? void 0 : b.id) && bw_accountInfoEqual(a, b)), (0,bw_external_rxjs_namespaceObject.shareReplay)({ bufferSize: 1, refCount: false }));
        this.accountActivity$ = this.globalStateProvider
            .get(bw_ACCOUNT_ACTIVITY)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((activity) => activity !== null && activity !== void 0 ? activity : {}));
        this.sortedUserIds$ = this.accountActivity$.pipe((0,bw_external_rxjs_namespaceObject.map)((activity) => {
            return Object.entries(activity)
                .map(([userId, lastActive]) => ({ userId, lastActive }))
                .sort((a, b) => b.lastActive.getTime() - a.lastActive.getTime()) // later dates first
                .map((a) => a.userId);
        }));
        this.nextUpAccount$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.accounts$,
            this.activeAccount$,
            this.sortedUserIds$,
        ]).pipe((0,bw_external_rxjs_namespaceObject.map)(([accounts, activeAccount, sortedUserIds]) => {
            const nextId = sortedUserIds.find((id) => id !== (activeAccount === null || activeAccount === void 0 ? void 0 : activeAccount.id) && accounts[id] != null);
            return nextId ? Object.assign({ id: nextId }, accounts[nextId]) : null;
        }));
        this.accountVerifyNewDeviceLogin$ = this.activeAccountIdState.state$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => this.singleUserStateProvider.get(userId, bw_ACCOUNT_VERIFY_NEW_DEVICE_LOGIN).state$));
    }
    addAccount(userId, accountData) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            if (!bw_utils_Utils.isGuid(userId)) {
                throw new Error("userId is required");
            }
            yield this.accountsState.update((accounts) => {
                accounts || (accounts = {});
                accounts[userId] = accountData;
                return accounts;
            });
            yield this.setAccountActivity(userId, new Date());
        });
    }
    setAccountName(userId, name) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            yield this.setAccountInfo(userId, { name });
        });
    }
    setAccountEmail(userId, email) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            yield this.setAccountInfo(userId, { email });
        });
    }
    setAccountEmailVerified(userId, emailVerified) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            yield this.setAccountInfo(userId, { emailVerified });
        });
    }
    clean(userId) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            yield this.setAccountInfo(userId, bw_LOGGED_OUT_INFO);
            yield this.removeAccountActivity(userId);
        });
    }
    switchAccount(userId) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            let updateActivity = false;
            yield this.activeAccountIdState.update((_, __) => {
                updateActivity = true;
                return userId;
            }, {
                combineLatestWith: this.accountsState.state$.pipe((0,bw_external_rxjs_namespaceObject.filter)((accounts) => {
                    if (userId == null) {
                        // Don't worry about accounts when we are about to set active user to null
                        return true;
                    }
                    return (accounts === null || accounts === void 0 ? void 0 : accounts[userId]) != null;
                }), 
                // If we don't get the desired account with enough time, just return empty as that will result in the same error
                (0,bw_external_rxjs_namespaceObject.timeout)({ first: 1000, with: () => (0,bw_external_rxjs_namespaceObject.of)({}) })),
                shouldUpdate: (id, accounts) => {
                    if (userId != null && (accounts === null || accounts === void 0 ? void 0 : accounts[userId]) == null) {
                        throw new Error("Account does not exist");
                    }
                    // update only if userId changes
                    return id !== userId;
                },
            });
            if (updateActivity) {
                yield this.setAccountActivity(userId, new Date());
            }
        });
    }
    setAccountActivity(userId, lastActivity) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            if (!bw_utils_Utils.isGuid(userId)) {
                // only store for valid userIds
                return;
            }
            yield this.globalStateProvider.get(bw_ACCOUNT_ACTIVITY).update((activity) => {
                activity || (activity = {});
                activity[userId] = lastActivity;
                return activity;
            }, {
                shouldUpdate: (oldActivity) => { var _a; return ((_a = oldActivity === null || oldActivity === void 0 ? void 0 : oldActivity[userId]) === null || _a === void 0 ? void 0 : _a.getTime()) !== (lastActivity === null || lastActivity === void 0 ? void 0 : lastActivity.getTime()); },
            });
        });
    }
    setAccountVerifyNewDeviceLogin(userId, setVerifyNewDeviceLogin) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            if (!bw_utils_Utils.isGuid(userId)) {
                // only store for valid userIds
                return;
            }
            yield this.singleUserStateProvider.get(userId, bw_ACCOUNT_VERIFY_NEW_DEVICE_LOGIN).update(() => {
                return setVerifyNewDeviceLogin;
            });
        });
    }
    removeAccountActivity(userId) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            yield this.globalStateProvider.get(bw_ACCOUNT_ACTIVITY).update((activity) => {
                if (activity == null) {
                    return activity;
                }
                delete activity[userId];
                return activity;
            }, { shouldUpdate: (oldActivity) => (oldActivity === null || oldActivity === void 0 ? void 0 : oldActivity[userId]) != null });
        });
    }
    // TODO: update to use our own account status settings. Requires inverting direction of state service accounts flow
    delete() {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            try {
                (_a = this.messagingService) === null || _a === void 0 ? void 0 : _a.send("logout");
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    setAccountInfo(userId, update) {
        return bw_account_service_awaiter(this, void 0, void 0, function* () {
            function newAccountInfo(oldAccountInfo) {
                return Object.assign(Object.assign({}, oldAccountInfo), update);
            }
            yield this.accountsState.update((accounts) => {
                accounts[userId] = newAccountInfo(accounts[userId]);
                return accounts;
            }, {
                // Avoid unnecessary updates
                // TODO: Faster comparison, maybe include a hash on the objects?
                shouldUpdate: (accounts) => {
                    if ((accounts === null || accounts === void 0 ? void 0 : accounts[userId]) == null) {
                        throw new Error("Account does not exist");
                    }
                    return !bw_accountInfoEqual(accounts[userId], newAccountInfo(accounts[userId]));
                },
            });
        });
    }
}

;// ../../libs/common/src/vault/models/data/card.data.ts
class bw_CardData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.cardholderName = data.cardholderName;
        this.brand = data.brand;
        this.number = data.number;
        this.expMonth = data.expMonth;
        this.expYear = data.expYear;
        this.code = data.code;
    }
}

;// ../../libs/common/src/autofill/constants/match-patterns.ts
const bw_CardExpiryDateDelimiters = ["/", "-", ".", " "];
// `CardExpiryDateDelimiters` is not intended solely for regex consumption,
// so we need to format it here
const bw_ExpiryDateDelimitersPattern = "\\" +
    bw_CardExpiryDateDelimiters.join("\\")
        // replace space character with the regex whitespace character class
        .replace(" ", "s");
const bw_MonthPattern = "(([1]{1}[0-2]{1})|(0?[1-9]{1}))";
// Because we're dealing with expiry dates, we assume the year will be in current or next century (as of 2024)
const bw_match_patterns_ExpiryFullYearPattern = "2[0-1]{1}\\d{2}";
const bw_match_patterns_DelimiterPatternExpression = new RegExp(`[${bw_ExpiryDateDelimitersPattern}]`, "g");
const bw_match_patterns_IrrelevantExpiryCharactersPatternExpression = new RegExp(
// "nor digits" to ensure numbers are removed from guidance pattern, which aren't covered by ^\w
`[^\\d${bw_ExpiryDateDelimitersPattern}]`, "g");
const bw_match_patterns_MonthPatternExpression = new RegExp(`^${bw_MonthPattern}$`);
const bw_match_patterns_ExpiryFullYearPatternExpression = new RegExp(`^${bw_match_patterns_ExpiryFullYearPattern}$`);

;// ../../libs/common/src/autofill/constants/index.ts
const bw_TYPE_CHECK = {
    FUNCTION: "function",
    NUMBER: "number",
    STRING: "string",
};
const bw_EVENTS = {
    CHANGE: "change",
    INPUT: "input",
    KEYDOWN: "keydown",
    KEYPRESS: "keypress",
    KEYUP: "keyup",
    BLUR: "blur",
    CLICK: "click",
    FOCUS: "focus",
    FOCUSIN: "focusin",
    FOCUSOUT: "focusout",
    SCROLL: "scroll",
    RESIZE: "resize",
    DOMCONTENTLOADED: "DOMContentLoaded",
    LOAD: "load",
    MESSAGE: "message",
    VISIBILITYCHANGE: "visibilitychange",
    MOUSEENTER: "mouseenter",
    MOUSELEAVE: "mouseleave",
    MOUSEUP: "mouseup",
    MOUSEOUT: "mouseout",
    SUBMIT: "submit",
};
const bw_ClearClipboardDelay = {
    Never: null,
    TenSeconds: 10,
    TwentySeconds: 20,
    ThirtySeconds: 30,
    OneMinute: 60,
    TwoMinutes: 120,
    FiveMinutes: 300,
};
/* Context Menu item Ids */
const bw_AUTOFILL_CARD_ID = "autofill-card";
const bw_AUTOFILL_ID = "autofill";
const bw_SHOW_AUTOFILL_BUTTON = "show-autofill-button";
const bw_AUTOFILL_IDENTITY_ID = "autofill-identity";
const bw_COPY_IDENTIFIER_ID = "copy-identifier";
const bw_COPY_PASSWORD_ID = "copy-password";
const bw_COPY_USERNAME_ID = "copy-username";
const bw_COPY_VERIFICATION_CODE_ID = "copy-totp";
const bw_CREATE_CARD_ID = "create-card";
const bw_CREATE_IDENTITY_ID = "create-identity";
const bw_CREATE_LOGIN_ID = "create-login";
const bw_GENERATE_PASSWORD_ID = "generate-password";
const bw_NOOP_COMMAND_SUFFIX = "noop";
const bw_ROOT_ID = "root";
const bw_SEPARATOR_ID = "separator";
const bw_NOTIFICATION_BAR_LIFESPAN_MS = 150000; // 150 seconds
const bw_AUTOFILL_OVERLAY_HANDLE_REPOSITION = "autofill-overlay-handle-reposition-event";
const bw_AUTOFILL_OVERLAY_HANDLE_SCROLL = "autofill-overlay-handle-scroll-event";
const bw_UPDATE_PASSKEYS_HEADINGS_ON_SCROLL = "update-passkeys-headings-on-scroll";
const bw_AUTOFILL_TRIGGER_FORM_FIELD_SUBMIT = "autofill-trigger-form-field-submit";
const bw_AutofillOverlayVisibility = {
    Off: 0,
    OnButtonClick: 1,
    OnFieldFocus: 2,
};
const bw_BrowserClientVendors = {
    Chrome: "Chrome",
    Opera: "Opera",
    Edge: "Edge",
    Vivaldi: "Vivaldi",
    Unknown: "Unknown",
};
const bw_BrowserShortcutsUris = {
    Chrome: "chrome://extensions/shortcuts",
    Opera: "opera://extensions/shortcuts",
    Edge: "edge://extensions/shortcuts",
    Vivaldi: "vivaldi://extensions/shortcuts",
    Unknown: "https://bitwarden.com/help/keyboard-shortcuts",
};
const bw_DisablePasswordManagerUris = {
    Chrome: "chrome://settings/autofill",
    Opera: "opera://settings/autofill",
    Edge: "edge://settings/passwords",
    Vivaldi: "vivaldi://settings/autofill",
    Unknown: "https://bitwarden.com/help/disable-browser-autofill/",
};
const bw_ExtensionCommand = {
    AutofillCommand: "autofill_cmd",
    AutofillCard: "autofill_card",
    AutofillIdentity: "autofill_identity",
    AutofillLogin: "autofill_login",
    OpenAutofillOverlay: "open_autofill_overlay",
    GeneratePassword: "generate_password",
    OpenPopup: "open_popup",
    LockVault: "lock_vault",
    NoopCommand: "noop",
};
const bw_CLEAR_NOTIFICATION_LOGIN_DATA_DURATION = (/* unused pure expression or super */ null && (60 * 1000)); // 1 minute
const bw_MAX_DEEP_QUERY_RECURSION_DEPTH = 4;


;// ../../libs/common/src/autofill/utils.ts


/**
 * Takes a string or number value and returns a string value formatted as a valid 4-digit year
 *
 * @param {(string | number)} yearInput
 * @return {*}  {(Year | null)}
 */
function bw_normalizeExpiryYearFormat(yearInput) {
    // The input[type="number"] is returning a number, convert it to a string
    // An empty field returns null, avoid casting `"null"` to a string
    const yearInputIsEmpty = yearInput == null || yearInput === "";
    let expirationYear = yearInputIsEmpty ? null : `${yearInput}`;
    // Exit early if year is already formatted correctly or empty
    if (yearInputIsEmpty || (expirationYear && /^[1-9]{1}\d{3}$/.test(expirationYear))) {
        return expirationYear;
    }
    expirationYear = (expirationYear || "")
        // For safety, because even input[type="number"] will allow decimals
        .replace(/[^\d]/g, "")
        // remove any leading zero padding (leave the last leading zero if it ends the string)
        .replace(/^[0]+(?=.)/, "");
    if (expirationYear === "") {
        expirationYear = null;
    }
    // given the context of payment card expiry, a year character length of 3, or over 4
    // is more likely to be a mistake than an intentional value for the far past or far future.
    if (expirationYear && expirationYear.length !== 4) {
        const paddedYear = ("00" + expirationYear).slice(-2);
        const currentCentury = `${new Date().getFullYear()}`.slice(0, 2);
        expirationYear = currentCentury + paddedYear;
    }
    return expirationYear;
}
/**
 * Takes a cipher card view and returns "true" if the month and year affirmativey indicate
 * the card is expired. Uncertain cases return "false".
 *
 * @param {CardView} cipherCard
 * @return {*}  {boolean}
 */
function bw_isCardExpired(cipherCard) {
    if (cipherCard) {
        const { expMonth = null, expYear = null } = cipherCard;
        if (!expYear) {
            return false;
        }
        const now = new Date();
        const normalizedYear = bw_normalizeExpiryYearFormat(expYear);
        const parsedYear = normalizedYear ? parseInt(normalizedYear, 10) : NaN;
        const expiryYearIsBeforeCurrentYear = parsedYear < now.getFullYear();
        const expiryYearIsAfterCurrentYear = parsedYear > now.getFullYear();
        // If the expiry year is before the current year, skip checking the month, since it must be expired
        if (normalizedYear && expiryYearIsBeforeCurrentYear) {
            return true;
        }
        // If the expiry year is after the current year, skip checking the month, since it cannot be expired
        if (normalizedYear && expiryYearIsAfterCurrentYear) {
            return false;
        }
        if (normalizedYear && expMonth) {
            const parsedMonthInteger = parseInt(expMonth, 10);
            const parsedMonthIsValid = parsedMonthInteger && !isNaN(parsedMonthInteger);
            // If the parsed month value is 0, we don't know when the expiry passes this year, so do not treat it as expired
            if (!parsedMonthIsValid) {
                return false;
            }
            // `Date` months are zero-indexed
            const parsedMonth = parsedMonthInteger - 1;
            // First day of the next month
            const cardExpiry = new Date(parsedYear, parsedMonth + 1, 1);
            return cardExpiry <= now;
        }
    }
    return false;
}
/**
 * Attempt to split a string into date segments on the basis of expected formats and delimiter symbols.
 *
 * @param {string} combinedExpiryValue
 * @return {*}  {string[]}
 */
function bw_splitCombinedDateValues(combinedExpiryValue) {
    var _a;
    let sanitizedValue = combinedExpiryValue
        .replace(IrrelevantExpiryCharactersPatternExpression, "")
        .trim();
    // Do this after initial value replace to avoid identifying leading whitespace as delimiter
    const parsedDelimiter = ((_a = sanitizedValue.match(DelimiterPatternExpression)) === null || _a === void 0 ? void 0 : _a[0]) || null;
    let dateParts = [sanitizedValue];
    if (parsedDelimiter === null || parsedDelimiter === void 0 ? void 0 : parsedDelimiter.length) {
        // If the parsed delimiter is a whitespace character, assign 's' (character class) instead
        const delimiterPattern = /\s/.test(parsedDelimiter) ? "\\s" : "\\" + parsedDelimiter;
        sanitizedValue = sanitizedValue
            // Remove all other delimiter characters not identified as the delimiter
            .replace(new RegExp(`[^\\d${delimiterPattern}]`, "g"), "")
            // Also de-dupe the delimiter character
            .replace(new RegExp(`[${delimiterPattern}]{2,}`, "g"), parsedDelimiter);
        dateParts = sanitizedValue.split(parsedDelimiter);
    }
    return (dateParts
        // remove values that have no length
        .filter((splitValue) => splitValue === null || splitValue === void 0 ? void 0 : splitValue.length));
}
/**
 * Given an array of split card expiry date parts,
 * returns an array of those values ordered by year then month
 *
 * @param {string[]} splitDateInput
 * @return {*}  {([string | null, string | null])}
 */
function bw_parseDelimitedYearMonthExpiry([firstPart, secondPart]) {
    // Conditionals here are structured to avoid unnecessary evaluations and are ordered
    // from more authoritative checks to checks yielding increasingly inferred conclusions
    // If a 4-digit value is found (when there are multiple parts), it can't be month
    if (ExpiryFullYearPatternExpression.test(firstPart)) {
        return [firstPart, secondPart];
    }
    // If a 4-digit value is found (when there are multiple parts), it can't be month
    if (ExpiryFullYearPatternExpression.test(secondPart)) {
        return [secondPart, firstPart];
    }
    // If it's a two digit value that doesn't match against month pattern, assume it's a year
    if (/\d{2}/.test(firstPart) && !MonthPatternExpression.test(firstPart)) {
        return [firstPart, secondPart];
    }
    // If it's a two digit value that doesn't match against month pattern, assume it's a year
    if (/\d{2}/.test(secondPart) && !MonthPatternExpression.test(secondPart)) {
        return [secondPart, firstPart];
    }
    // Values are too ambiguous (e.g. "12/09"). For the most part,
    // a month-looking value likely is, at the time of writing (year 2024).
    let parsedYear = firstPart;
    let parsedMonth = secondPart;
    if (MonthPatternExpression.test(firstPart)) {
        parsedYear = secondPart;
        parsedMonth = firstPart;
    }
    return [parsedYear, parsedMonth];
}
/**
 * Given a single string of integers, attempts to identify card expiry date portions within
 * and return values ordered by year then month
 *
 * @param {string} dateInput
 * @return {*}  {([string | null, string | null])}
 */
function bw_parseNonDelimitedYearMonthExpiry(dateInput) {
    if (dateInput.length > 4) {
        // e.g.
        // "052024"
        // "202405"
        // "20245"
        // "52024"
        // If the value is over 5-characters long, it likely has a full year format in it
        const [parsedYear, parsedMonth] = dateInput
            .split(new RegExp(`(?=${ExpiryFullYearPattern})|(?<=${ExpiryFullYearPattern})`, "g"))
            .sort((current, next) => (current.length > next.length ? -1 : 1));
        return [parsedYear, parsedMonth];
    }
    if (dateInput.length === 4) {
        // e.g.
        // "0524"
        // "2405"
        // If the `sanitizedFirstPart` value is a length of 4, it must be split in half, since
        // neither a year or month will be represented with three characters
        const splitFirstPartFirstHalf = dateInput.slice(0, 2);
        const splitFirstPartSecondHalf = dateInput.slice(-2);
        let parsedYear = splitFirstPartSecondHalf;
        let parsedMonth = splitFirstPartFirstHalf;
        // If the first part doesn't match a month pattern, assume it's a year
        if (!MonthPatternExpression.test(splitFirstPartFirstHalf)) {
            parsedYear = splitFirstPartFirstHalf;
            parsedMonth = splitFirstPartSecondHalf;
        }
        return [parsedYear, parsedMonth];
    }
    // e.g.
    // "245"
    // "202"
    // "212"
    // "022"
    // "111"
    // A valid year representation here must be two characters so try to find it first.
    let parsedYear = null;
    let parsedMonth = null;
    // Split if there is a digit with a leading zero
    const splitFirstPartOnLeadingZero = dateInput.split(/(?<=0[1-9]{1})|(?=0[1-9]{1})/);
    // Assume a leading zero indicates a month in ambiguous cases (e.g. "202"), since we're
    // dealing with expiry dates and the next two-digit year with a leading zero will be 2100
    if (splitFirstPartOnLeadingZero.length > 1) {
        parsedYear = splitFirstPartOnLeadingZero[0];
        parsedMonth = splitFirstPartOnLeadingZero[1];
        if (splitFirstPartOnLeadingZero[0].startsWith("0")) {
            parsedMonth = splitFirstPartOnLeadingZero[0];
            parsedYear = splitFirstPartOnLeadingZero[1];
        }
    }
    else {
        // Here, a year has to be two-digits, and a month can't be more than one, so assume the first two digits that are greater than the current year is the year representation.
        parsedYear = dateInput.slice(0, 2);
        parsedMonth = dateInput.slice(-1);
        const currentYear = new Date().getFullYear();
        const normalizedYearFormat = bw_normalizeExpiryYearFormat(parsedYear);
        const normalizedParsedYear = normalizedYearFormat && parseInt(normalizedYearFormat, 10);
        const normalizedExpiryYearFormat = bw_normalizeExpiryYearFormat(dateInput.slice(-2));
        const normalizedParsedYearAlternative = normalizedExpiryYearFormat && parseInt(normalizedExpiryYearFormat, 10);
        if (normalizedParsedYear &&
            normalizedParsedYear < currentYear &&
            normalizedParsedYearAlternative &&
            normalizedParsedYearAlternative >= currentYear) {
            parsedYear = dateInput.slice(-2);
            parsedMonth = dateInput.slice(0, 1);
        }
    }
    return [parsedYear, parsedMonth];
}
/**
 * Attempt to parse year and month parts of a combined expiry date value.
 *
 * @param {string} combinedExpiryValue
 * @return {*}  {([string | null, string | null])}
 */
function bw_parseYearMonthExpiry(combinedExpiryValue) {
    var _a, _b;
    let parsedYear = null;
    let parsedMonth = null;
    const dateParts = bw_splitCombinedDateValues(combinedExpiryValue);
    if (dateParts.length < 1) {
        return [null, null];
    }
    const sanitizedFirstPart = ((_a = dateParts[0]) === null || _a === void 0 ? void 0 : _a.replace(IrrelevantExpiryCharactersPatternExpression, "")) || "";
    const sanitizedSecondPart = ((_b = dateParts[1]) === null || _b === void 0 ? void 0 : _b.replace(IrrelevantExpiryCharactersPatternExpression, "")) || "";
    // If there is only one date part, no delimiter was found in the passed value
    if (dateParts.length === 1) {
        const [parsedNonDelimitedYear, parsedNonDelimitedMonth] = bw_parseNonDelimitedYearMonthExpiry(sanitizedFirstPart);
        parsedYear = parsedNonDelimitedYear;
        parsedMonth = parsedNonDelimitedMonth;
    }
    // There are multiple date parts
    else {
        const [parsedDelimitedYear, parsedDelimitedMonth] = bw_parseDelimitedYearMonthExpiry([
            sanitizedFirstPart,
            sanitizedSecondPart,
        ]);
        parsedYear = parsedDelimitedYear;
        parsedMonth = parsedDelimitedMonth;
    }
    const normalizedParsedYear = parsedYear ? bw_normalizeExpiryYearFormat(parsedYear) : null;
    const normalizedParsedMonth = parsedMonth === null || parsedMonth === void 0 ? void 0 : parsedMonth.replace(/^0+/, "").slice(0, 2);
    // Set "empty" values to null
    parsedYear = (normalizedParsedYear === null || normalizedParsedYear === void 0 ? void 0 : normalizedParsedYear.length) ? normalizedParsedYear : null;
    parsedMonth = (normalizedParsedMonth === null || normalizedParsedMonth === void 0 ? void 0 : normalizedParsedMonth.length) ? normalizedParsedMonth : null;
    return [parsedYear, parsedMonth];
}
/**
 * Takes a URL string and a NeverDomains object and determines if the passed URL's hostname is in `urlList`
 *
 * @param {string} url - representation of URL to check
 * @param {NeverDomains} urlList - object with hostname key names
 */
function bw_isUrlInList(url = "", urlList = {}) {
    const urlListKeys = urlList && Object.keys(urlList);
    if (urlListKeys.length && (url === null || url === void 0 ? void 0 : url.length)) {
        let tabHostname;
        try {
            tabHostname = Utils.getHostname(url);
        }
        catch (_a) {
            // If the input was invalid, exit early and return false
            return false;
        }
        if (tabHostname) {
            return urlListKeys.some((blockedHostname) => tabHostname.endsWith(blockedHostname));
        }
    }
    return false;
}

;// ../../libs/common/src/vault/enums/cipher-reprompt-type.ts
var bw_CipherRepromptType;
(function (CipherRepromptType) {
    CipherRepromptType[CipherRepromptType["None"] = 0] = "None";
    CipherRepromptType[CipherRepromptType["Password"] = 1] = "Password";
})(bw_CipherRepromptType || (bw_CipherRepromptType = {}));

;// ../../libs/common/src/vault/enums/cipher-type.ts
var bw_CipherType;
(function (CipherType) {
    CipherType[CipherType["Login"] = 1] = "Login";
    CipherType[CipherType["SecureNote"] = 2] = "SecureNote";
    CipherType[CipherType["Card"] = 3] = "Card";
    CipherType[CipherType["Identity"] = 4] = "Identity";
    CipherType[CipherType["SshKey"] = 5] = "SshKey";
})(bw_CipherType || (bw_CipherType = {}));

;// ../../libs/common/src/vault/enums/field-type.enum.ts
var bw_FieldType;
(function (FieldType) {
    FieldType[FieldType["Text"] = 0] = "Text";
    FieldType[FieldType["Hidden"] = 1] = "Hidden";
    FieldType[FieldType["Boolean"] = 2] = "Boolean";
    FieldType[FieldType["Linked"] = 3] = "Linked";
})(bw_FieldType || (bw_FieldType = {}));

;// ../../libs/common/src/vault/enums/linked-id-type.enum.ts
// LoginView
var bw_LoginLinkedId;
(function (LoginLinkedId) {
    LoginLinkedId[LoginLinkedId["Username"] = 100] = "Username";
    LoginLinkedId[LoginLinkedId["Password"] = 101] = "Password";
})(bw_LoginLinkedId || (bw_LoginLinkedId = {}));
// CardView
var bw_CardLinkedId;
(function (CardLinkedId) {
    CardLinkedId[CardLinkedId["CardholderName"] = 300] = "CardholderName";
    CardLinkedId[CardLinkedId["ExpMonth"] = 301] = "ExpMonth";
    CardLinkedId[CardLinkedId["ExpYear"] = 302] = "ExpYear";
    CardLinkedId[CardLinkedId["Code"] = 303] = "Code";
    CardLinkedId[CardLinkedId["Brand"] = 304] = "Brand";
    CardLinkedId[CardLinkedId["Number"] = 305] = "Number";
})(bw_CardLinkedId || (bw_CardLinkedId = {}));
// IdentityView
var bw_IdentityLinkedId;
(function (IdentityLinkedId) {
    IdentityLinkedId[IdentityLinkedId["Title"] = 400] = "Title";
    IdentityLinkedId[IdentityLinkedId["MiddleName"] = 401] = "MiddleName";
    IdentityLinkedId[IdentityLinkedId["Address1"] = 402] = "Address1";
    IdentityLinkedId[IdentityLinkedId["Address2"] = 403] = "Address2";
    IdentityLinkedId[IdentityLinkedId["Address3"] = 404] = "Address3";
    IdentityLinkedId[IdentityLinkedId["City"] = 405] = "City";
    IdentityLinkedId[IdentityLinkedId["State"] = 406] = "State";
    IdentityLinkedId[IdentityLinkedId["PostalCode"] = 407] = "PostalCode";
    IdentityLinkedId[IdentityLinkedId["Country"] = 408] = "Country";
    IdentityLinkedId[IdentityLinkedId["Company"] = 409] = "Company";
    IdentityLinkedId[IdentityLinkedId["Email"] = 410] = "Email";
    IdentityLinkedId[IdentityLinkedId["Phone"] = 411] = "Phone";
    IdentityLinkedId[IdentityLinkedId["Ssn"] = 412] = "Ssn";
    IdentityLinkedId[IdentityLinkedId["Username"] = 413] = "Username";
    IdentityLinkedId[IdentityLinkedId["PassportNumber"] = 414] = "PassportNumber";
    IdentityLinkedId[IdentityLinkedId["LicenseNumber"] = 415] = "LicenseNumber";
    IdentityLinkedId[IdentityLinkedId["FirstName"] = 416] = "FirstName";
    IdentityLinkedId[IdentityLinkedId["LastName"] = 417] = "LastName";
    IdentityLinkedId[IdentityLinkedId["FullName"] = 418] = "FullName";
})(bw_IdentityLinkedId || (bw_IdentityLinkedId = {}));

;// ../../libs/common/src/vault/enums/secure-note-type.enum.ts
var bw_SecureNoteType;
(function (SecureNoteType) {
    SecureNoteType[SecureNoteType["Generic"] = 0] = "Generic";
})(bw_SecureNoteType || (bw_SecureNoteType = {}));

;// ../../libs/common/src/vault/enums/index.ts






;// ../../libs/common/src/vault/linked-field-option.decorator.ts
class bw_LinkedMetadata {
    constructor(propertyKey, attributes) {
        this.propertyKey = propertyKey;
        this._i18nKey = attributes === null || attributes === void 0 ? void 0 : attributes.i18nKey;
        this.sortPosition = attributes.sortPosition;
    }
    get i18nKey() {
        var _a;
        return (_a = this._i18nKey) !== null && _a !== void 0 ? _a : this.propertyKey;
    }
}
/**
 * A decorator used to set metadata used by Linked custom fields. Apply it to a class property or getter to make it
 *    available as a Linked custom field option.
 * @param id - A unique value that is saved in the Field model. It is used to look up the decorated class property.
 * @param options - {@link LinkedMetadataAttributes}
 */
function bw_linkedFieldOption(id, attributes) {
    return (prototype, propertyKey) => {
        if (prototype.linkedFieldOptions == null) {
            prototype.linkedFieldOptions = new Map();
        }
        prototype.linkedFieldOptions.set(id, new bw_LinkedMetadata(propertyKey, attributes));
    };
}

;// ../../libs/common/src/vault/models/view/item.view.ts
class bw_ItemView {
}

;// ../../libs/common/src/vault/models/view/card.view.ts
var bw_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};




class bw_CardView extends bw_ItemView {
    constructor() {
        super(...arguments);
        this.cardholderName = null;
        this.expMonth = null;
        this.expYear = null;
        this.code = null;
        this._brand = null;
        this._number = null;
        this._subTitle = null;
    }
    get maskedCode() {
        return this.code != null ? "•".repeat(this.code.length) : null;
    }
    get maskedNumber() {
        return this.number != null ? "•".repeat(this.number.length) : null;
    }
    get brand() {
        return this._brand;
    }
    set brand(value) {
        this._brand = value;
        this._subTitle = null;
    }
    get number() {
        return this._number;
    }
    set number(value) {
        this._number = value;
        this._subTitle = null;
    }
    get subTitle() {
        if (this._subTitle == null) {
            this._subTitle = this.brand;
            if (this.number != null && this.number.length >= 4) {
                if (this._subTitle != null && this._subTitle !== "") {
                    this._subTitle += ", ";
                }
                else {
                    this._subTitle = "";
                }
                // Show last 5 on amex, last 4 for all others
                const count = this.number.length >= 5 && this.number.match(new RegExp("^3[47]")) != null ? 5 : 4;
                this._subTitle += "*" + this.number.substr(this.number.length - count);
            }
        }
        return this._subTitle;
    }
    get expiration() {
        const normalizedYear = bw_normalizeExpiryYearFormat(this.expYear);
        if (!this.expMonth && !normalizedYear) {
            return null;
        }
        let exp = this.expMonth != null ? ("0" + this.expMonth).slice(-2) : "__";
        exp += " / " + (normalizedYear || "____");
        return exp;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_CardView(), obj);
    }
    // ref https://stackoverflow.com/a/5911300
    static getCardBrandByPatterns(cardNum) {
        if (cardNum == null || typeof cardNum !== "string" || cardNum.trim() === "") {
            return null;
        }
        // Visa
        let re = new RegExp("^4");
        if (cardNum.match(re) != null) {
            return "Visa";
        }
        // Mastercard
        // Updated for Mastercard 2017 BINs expansion
        if (/^(5[1-5][0-9]{14}|2(22[1-9][0-9]{12}|2[3-9][0-9]{13}|[3-6][0-9]{14}|7[0-1][0-9]{13}|720[0-9]{12}))$/.test(cardNum)) {
            return "Mastercard";
        }
        // AMEX
        re = new RegExp("^3[47]");
        if (cardNum.match(re) != null) {
            return "Amex";
        }
        // Discover
        re = new RegExp("^(6011|622(12[6-9]|1[3-9][0-9]|[2-8][0-9]{2}|9[0-1][0-9]|92[0-5]|64[4-9])|65)");
        if (cardNum.match(re) != null) {
            return "Discover";
        }
        // Diners
        re = new RegExp("^36");
        if (cardNum.match(re) != null) {
            return "Diners Club";
        }
        // Diners - Carte Blanche
        re = new RegExp("^30[0-5]");
        if (cardNum.match(re) != null) {
            return "Diners Club";
        }
        // JCB
        re = new RegExp("^35(2[89]|[3-8][0-9])");
        if (cardNum.match(re) != null) {
            return "JCB";
        }
        // Visa Electron
        re = new RegExp("^(4026|417500|4508|4844|491(3|7))");
        if (cardNum.match(re) != null) {
            return "Visa";
        }
        return null;
    }
}
bw_decorate([
    bw_linkedFieldOption(bw_CardLinkedId.CardholderName, { sortPosition: 0 }),
    bw_metadata("design:type", String)
], bw_CardView.prototype, "cardholderName", void 0);
bw_decorate([
    bw_linkedFieldOption(bw_CardLinkedId.ExpMonth, { sortPosition: 3, i18nKey: "expirationMonth" }),
    bw_metadata("design:type", String)
], bw_CardView.prototype, "expMonth", void 0);
bw_decorate([
    bw_linkedFieldOption(bw_CardLinkedId.ExpYear, { sortPosition: 4, i18nKey: "expirationYear" }),
    bw_metadata("design:type", String)
], bw_CardView.prototype, "expYear", void 0);
bw_decorate([
    bw_linkedFieldOption(bw_CardLinkedId.Code, { sortPosition: 5, i18nKey: "securityCode" }),
    bw_metadata("design:type", String)
], bw_CardView.prototype, "code", void 0);
bw_decorate([
    bw_linkedFieldOption(bw_CardLinkedId.Brand, { sortPosition: 2 }),
    bw_metadata("design:type", String),
    bw_metadata("design:paramtypes", [String])
], bw_CardView.prototype, "brand", null);
bw_decorate([
    bw_linkedFieldOption(bw_CardLinkedId.Number, { sortPosition: 1 }),
    bw_metadata("design:type", String),
    bw_metadata("design:paramtypes", [String])
], bw_CardView.prototype, "number", null);

;// ../../libs/common/src/vault/models/domain/card.ts
var bw_card_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_Card extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            cardholderName: null,
            brand: null,
            number: null,
            expMonth: null,
            expYear: null,
            code: null,
        }, []);
    }
    decrypt(orgId_1) {
        return bw_card_awaiter(this, arguments, void 0, function* (orgId, context = "No Cipher Context", encKey) {
            return this.decryptObj(this, new bw_CardView(), ["cardholderName", "brand", "number", "expMonth", "expYear", "code"], orgId, encKey, "DomainType: Card; " + context);
        });
    }
    toCardData() {
        const c = new bw_CardData();
        this.buildDataModel(this, c, {
            cardholderName: null,
            brand: null,
            number: null,
            expMonth: null,
            expYear: null,
            code: null,
        });
        return c;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const cardholderName = bw_enc_string_EncString.fromJSON(obj.cardholderName);
        const brand = bw_enc_string_EncString.fromJSON(obj.brand);
        const number = bw_enc_string_EncString.fromJSON(obj.number);
        const expMonth = bw_enc_string_EncString.fromJSON(obj.expMonth);
        const expYear = bw_enc_string_EncString.fromJSON(obj.expYear);
        const code = bw_enc_string_EncString.fromJSON(obj.code);
        return Object.assign(new bw_Card(), obj, {
            cardholderName,
            brand,
            number,
            expMonth,
            expYear,
            code,
        });
    }
}

;// ../../libs/common/src/models/export/utils.ts
function bw_safeGetString(value) {
    if (value == null) {
        return null;
    }
    if (typeof value == "string") {
        return value;
    }
    return value === null || value === void 0 ? void 0 : value.encryptedString;
}

;// ../../libs/common/src/models/export/card.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_CardExport {
    static template() {
        const req = new bw_CardExport();
        req.cardholderName = "John Doe";
        req.brand = "visa";
        req.number = "4242424242424242";
        req.expMonth = "04";
        req.expYear = "2023";
        req.code = "123";
        return req;
    }
    static toView(req, view = new bw_CardView()) {
        view.cardholderName = req.cardholderName;
        view.brand = req.brand;
        view.number = req.number;
        view.expMonth = req.expMonth;
        view.expYear = req.expYear;
        view.code = req.code;
        return view;
    }
    static toDomain(req, domain = new bw_Card()) {
        domain.cardholderName = req.cardholderName != null ? new bw_enc_string_EncString(req.cardholderName) : null;
        domain.brand = req.brand != null ? new bw_enc_string_EncString(req.brand) : null;
        domain.number = req.number != null ? new bw_enc_string_EncString(req.number) : null;
        domain.expMonth = req.expMonth != null ? new bw_enc_string_EncString(req.expMonth) : null;
        domain.expYear = req.expYear != null ? new bw_enc_string_EncString(req.expYear) : null;
        domain.code = req.code != null ? new bw_enc_string_EncString(req.code) : null;
        return domain;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.cardholderName = bw_safeGetString(o.cardholderName);
        this.brand = bw_safeGetString(o.brand);
        this.number = bw_safeGetString(o.number);
        this.expMonth = bw_safeGetString(o.expMonth);
        this.expYear = bw_safeGetString(o.expYear);
        this.code = bw_safeGetString(o.code);
    }
}

;// ../../libs/common/src/platform/services/cryptography/initializer-key.ts
var bw_InitializerKey;
(function (InitializerKey) {
    InitializerKey[InitializerKey["Cipher"] = 0] = "Cipher";
    InitializerKey[InitializerKey["CipherView"] = 1] = "CipherView";
})(bw_InitializerKey || (bw_InitializerKey = {}));

;// ../../libs/common/src/vault/models/api/cipher-permissions.api.ts

class bw_CipherPermissionsApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        this.delete = false;
        this.restore = false;
        if (data == null) {
            return;
        }
        this.delete = this.getResponseProperty("Delete");
        this.restore = this.getResponseProperty("Restore");
    }
    static fromJSON(obj) {
        return Object.assign(new bw_CipherPermissionsApi(), obj);
    }
}

;// ../../libs/common/src/vault/models/data/attachment.data.ts
class bw_AttachmentData {
    constructor(response) {
        if (response == null) {
            return;
        }
        this.id = response.id;
        this.url = response.url;
        this.fileName = response.fileName;
        this.key = response.key;
        this.size = response.size;
        this.sizeName = response.sizeName;
    }
}

;// ../../libs/common/src/vault/models/data/field.data.ts
class bw_FieldData {
    constructor(response) {
        if (response == null) {
            return;
        }
        this.type = response.type;
        this.name = response.name;
        this.value = response.value;
        this.linkedId = response.linkedId;
    }
}

;// ../../libs/common/src/vault/models/data/identity.data.ts
class bw_IdentityData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.title = data.title;
        this.firstName = data.firstName;
        this.middleName = data.middleName;
        this.lastName = data.lastName;
        this.address1 = data.address1;
        this.address2 = data.address2;
        this.address3 = data.address3;
        this.city = data.city;
        this.state = data.state;
        this.postalCode = data.postalCode;
        this.country = data.country;
        this.company = data.company;
        this.email = data.email;
        this.phone = data.phone;
        this.ssn = data.ssn;
        this.username = data.username;
        this.passportNumber = data.passportNumber;
        this.licenseNumber = data.licenseNumber;
    }
}

;// ../../libs/common/src/vault/models/data/fido2-credential.data.ts
class bw_Fido2CredentialData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.credentialId = data.credentialId;
        this.keyType = data.keyType;
        this.keyAlgorithm = data.keyAlgorithm;
        this.keyCurve = data.keyCurve;
        this.keyValue = data.keyValue;
        this.rpId = data.rpId;
        this.userHandle = data.userHandle;
        this.userName = data.userName;
        this.counter = data.counter;
        this.rpName = data.rpName;
        this.userDisplayName = data.userDisplayName;
        this.discoverable = data.discoverable;
        this.creationDate = data.creationDate;
    }
}

;// ../../libs/common/src/vault/models/data/login-uri.data.ts
class bw_LoginUriData {
    constructor(data) {
        this.match = null;
        if (data == null) {
            return;
        }
        this.uri = data.uri;
        this.uriChecksum = data.uriChecksum;
        this.match = data.match;
    }
}

;// ../../libs/common/src/vault/models/data/login.data.ts


class bw_LoginData {
    constructor(data) {
        var _a;
        if (data == null) {
            return;
        }
        this.username = data.username;
        this.password = data.password;
        this.passwordRevisionDate = data.passwordRevisionDate;
        this.totp = data.totp;
        this.autofillOnPageLoad = data.autofillOnPageLoad;
        if (data.uris) {
            this.uris = data.uris.map((u) => new bw_LoginUriData(u));
        }
        if (data.fido2Credentials) {
            this.fido2Credentials = (_a = data.fido2Credentials) === null || _a === void 0 ? void 0 : _a.map((key) => new bw_Fido2CredentialData(key));
        }
    }
}

;// ../../libs/common/src/vault/models/data/password-history.data.ts
class bw_PasswordHistoryData {
    constructor(response) {
        if (response == null) {
            return;
        }
        this.password = response.password;
        this.lastUsedDate = response.lastUsedDate;
    }
}

;// ../../libs/common/src/vault/models/data/secure-note.data.ts
class bw_SecureNoteData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.type = data.type;
    }
}

;// ../../libs/common/src/vault/models/data/ssh-key.data.ts
class bw_SshKeyData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.privateKey = data.privateKey;
        this.publicKey = data.publicKey;
        this.keyFingerprint = data.keyFingerprint;
    }
}

;// ../../libs/common/src/vault/models/data/cipher.data.ts










class bw_CipherData {
    constructor(response, collectionIds) {
        if (response == null) {
            return;
        }
        this.id = response.id;
        this.organizationId = response.organizationId;
        this.folderId = response.folderId;
        this.edit = response.edit;
        this.viewPassword = response.viewPassword;
        this.permissions = response.permissions;
        this.organizationUseTotp = response.organizationUseTotp;
        this.favorite = response.favorite;
        this.revisionDate = response.revisionDate;
        this.type = response.type;
        this.name = response.name;
        this.notes = response.notes;
        this.collectionIds = collectionIds != null ? collectionIds : response.collectionIds;
        this.creationDate = response.creationDate;
        this.deletedDate = response.deletedDate;
        this.reprompt = response.reprompt;
        this.key = response.key;
        switch (this.type) {
            case bw_CipherType.Login:
                this.login = new bw_LoginData(response.login);
                break;
            case bw_CipherType.SecureNote:
                this.secureNote = new bw_SecureNoteData(response.secureNote);
                break;
            case bw_CipherType.Card:
                this.card = new bw_CardData(response.card);
                break;
            case bw_CipherType.Identity:
                this.identity = new bw_IdentityData(response.identity);
                break;
            case bw_CipherType.SshKey:
                this.sshKey = new bw_SshKeyData(response.sshKey);
                break;
            default:
                break;
        }
        if (response.fields != null) {
            this.fields = response.fields.map((f) => new bw_FieldData(f));
        }
        if (response.attachments != null) {
            this.attachments = response.attachments.map((a) => new bw_AttachmentData(a));
        }
        if (response.passwordHistory != null) {
            this.passwordHistory = response.passwordHistory.map((ph) => new bw_PasswordHistoryData(ph));
        }
    }
    static fromJSON(obj) {
        const result = Object.assign(new bw_CipherData(), obj);
        result.permissions = bw_CipherPermissionsApi.fromJSON(obj.permissions);
        return result;
    }
}

;// ../../libs/common/src/vault/models/view/attachment.view.ts

class bw_AttachmentView {
    constructor(a) {
        this.id = null;
        this.url = null;
        this.size = null;
        this.sizeName = null;
        this.fileName = null;
        this.key = null;
        if (!a) {
            return;
        }
        this.id = a.id;
        this.url = a.url;
        this.size = a.size;
        this.sizeName = a.sizeName;
    }
    get fileSize() {
        try {
            if (this.size != null) {
                return parseInt(this.size, null);
            }
        }
        catch (_a) {
            // Invalid file size.
        }
        return 0;
    }
    static fromJSON(obj) {
        const key = obj.key == null ? null : bw_SymmetricCryptoKey.fromJSON(obj.key);
        return Object.assign(new bw_AttachmentView(), obj, { key: key });
    }
}

;// ../../libs/common/src/vault/models/view/field.view.ts
class bw_FieldView {
    constructor(f) {
        this.name = null;
        this.value = null;
        this.type = null;
        this.newField = false; // Marks if the field is new and hasn't been saved
        this.showValue = false;
        this.showCount = false;
        this.linkedId = null;
        if (!f) {
            return;
        }
        this.type = f.type;
        this.linkedId = f.linkedId;
    }
    get maskedValue() {
        return this.value != null ? "••••••••" : null;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_FieldView(), obj);
    }
}

;// ../../libs/common/src/vault/models/view/identity.view.ts
var bw_identity_view_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_identity_view_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};




class bw_IdentityView extends bw_ItemView {
    constructor() {
        super();
        this.title = null;
        this.middleName = null;
        this.address1 = null;
        this.address2 = null;
        this.address3 = null;
        this.city = null;
        this.state = null;
        this.postalCode = null;
        this.country = null;
        this.company = null;
        this.email = null;
        this.phone = null;
        this.ssn = null;
        this.username = null;
        this.passportNumber = null;
        this.licenseNumber = null;
        this._firstName = null;
        this._lastName = null;
        this._subTitle = null;
    }
    get firstName() {
        return this._firstName;
    }
    set firstName(value) {
        this._firstName = value;
        this._subTitle = null;
    }
    get lastName() {
        return this._lastName;
    }
    set lastName(value) {
        this._lastName = value;
        this._subTitle = null;
    }
    get subTitle() {
        if (this._subTitle == null && (this.firstName != null || this.lastName != null)) {
            this._subTitle = "";
            if (this.firstName != null) {
                this._subTitle = this.firstName;
            }
            if (this.lastName != null) {
                if (this._subTitle !== "") {
                    this._subTitle += " ";
                }
                this._subTitle += this.lastName;
            }
        }
        return this._subTitle;
    }
    get fullName() {
        if (this.title != null ||
            this.firstName != null ||
            this.middleName != null ||
            this.lastName != null) {
            let name = "";
            if (this.title != null) {
                name += this.title + " ";
            }
            if (this.firstName != null) {
                name += this.firstName + " ";
            }
            if (this.middleName != null) {
                name += this.middleName + " ";
            }
            if (this.lastName != null) {
                name += this.lastName;
            }
            return name.trim();
        }
        return null;
    }
    get fullAddress() {
        let address = this.address1;
        if (!bw_utils_Utils.isNullOrWhitespace(this.address2)) {
            if (!bw_utils_Utils.isNullOrWhitespace(address)) {
                address += ", ";
            }
            address += this.address2;
        }
        if (!bw_utils_Utils.isNullOrWhitespace(this.address3)) {
            if (!bw_utils_Utils.isNullOrWhitespace(address)) {
                address += ", ";
            }
            address += this.address3;
        }
        return address;
    }
    get fullAddressPart2() {
        if (this.city == null && this.state == null && this.postalCode == null) {
            return null;
        }
        const city = this.city || "-";
        const state = this.state;
        const postalCode = this.postalCode || "-";
        let addressPart2 = city;
        if (!bw_utils_Utils.isNullOrWhitespace(state)) {
            addressPart2 += ", " + state;
        }
        addressPart2 += ", " + postalCode;
        return addressPart2;
    }
    get fullAddressForCopy() {
        let address = this.fullAddress;
        if (this.city != null || this.state != null || this.postalCode != null) {
            address += "\n" + this.fullAddressPart2;
        }
        if (this.country != null) {
            address += "\n" + this.country;
        }
        return address;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_IdentityView(), obj);
    }
}
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Title, { sortPosition: 0 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "title", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.MiddleName, { sortPosition: 2 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "middleName", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Address1, { sortPosition: 12 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "address1", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Address2, { sortPosition: 13 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "address2", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Address3, { sortPosition: 14 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "address3", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.City, { sortPosition: 15, i18nKey: "cityTown" }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "city", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.State, { sortPosition: 16, i18nKey: "stateProvince" }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "state", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.PostalCode, { sortPosition: 17, i18nKey: "zipPostalCode" }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "postalCode", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Country, { sortPosition: 18 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "country", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Company, { sortPosition: 6 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "company", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Email, { sortPosition: 10 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "email", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Phone, { sortPosition: 11 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "phone", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Ssn, { sortPosition: 7 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "ssn", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.Username, { sortPosition: 5 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "username", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.PassportNumber, { sortPosition: 8 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "passportNumber", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.LicenseNumber, { sortPosition: 9 }),
    bw_identity_view_metadata("design:type", String)
], bw_IdentityView.prototype, "licenseNumber", void 0);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.FirstName, { sortPosition: 1 }),
    bw_identity_view_metadata("design:type", String),
    bw_identity_view_metadata("design:paramtypes", [String])
], bw_IdentityView.prototype, "firstName", null);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.LastName, { sortPosition: 4 }),
    bw_identity_view_metadata("design:type", String),
    bw_identity_view_metadata("design:paramtypes", [String])
], bw_IdentityView.prototype, "lastName", null);
bw_identity_view_decorate([
    bw_linkedFieldOption(bw_IdentityLinkedId.FullName, { sortPosition: 3 }),
    bw_identity_view_metadata("design:type", String),
    bw_identity_view_metadata("design:paramtypes", [])
], bw_IdentityView.prototype, "fullName", null);

;// ../../libs/common/src/vault/models/view/fido2-credential.view.ts

class bw_Fido2CredentialView extends bw_ItemView {
    constructor() {
        super(...arguments);
        this.creationDate = null;
    }
    get subTitle() {
        return this.userDisplayName;
    }
    static fromJSON(obj) {
        const creationDate = obj.creationDate != null ? new Date(obj.creationDate) : null;
        return Object.assign(new bw_Fido2CredentialView(), obj, {
            creationDate,
        });
    }
}

;// ../../libs/common/src/models/domain/domain-service.ts
/*
  See full documentation at:
    https://bitwarden.com/help/uri-match-detection/#match-detection-options

  Domain: "the top-level domain and second-level domain of the URI match the detected resource",
  Host: "the hostname and (if specified) port of the URI matches the detected resource",
  StartsWith: "the detected resource starts with the URI, regardless of what follows it",
  Exact: "the URI matches the detected resource exactly",
  RegularExpression: "the detected resource matches a specified regular expression",
  Never: "never offer auto-fill for the item",
*/
const bw_UriMatchStrategy = {
    Domain: 0,
    Host: 1,
    StartsWith: 2,
    Exact: 3,
    RegularExpression: 4,
    Never: 5,
};

;// ../../libs/common/src/platform/misc/safe-urls.ts

const bw_CanLaunchWhitelist = [
    "https://",
    "http://",
    "ssh://",
    "ftp://",
    "sftp://",
    "irc://",
    "vnc://",
    // https://docs.microsoft.com/en-us/windows-server/remote/remote-desktop-services/clients/remote-desktop-uri
    "rdp://", // Legacy RDP URI scheme
    "ms-rd:", // Preferred RDP URI scheme
    "chrome://",
    "iosapp://",
    "androidapp://",
];
class bw_SafeUrls {
    static canLaunch(uri) {
        if (bw_utils_Utils.isNullOrWhitespace(uri)) {
            return false;
        }
        for (let i = 0; i < bw_CanLaunchWhitelist.length; i++) {
            if (uri.indexOf(bw_CanLaunchWhitelist[i]) === 0) {
                return true;
            }
        }
        return false;
    }
}

;// ../../libs/common/src/vault/models/view/login-uri.view.ts



class bw_LoginUriView {
    constructor(u) {
        this.match = null;
        this._uri = null;
        this._domain = null;
        this._hostname = null;
        this._host = null;
        this._canLaunch = null;
        if (!u) {
            return;
        }
        this.match = u.match;
    }
    get uri() {
        return this._uri;
    }
    set uri(value) {
        this._uri = value;
        this._domain = null;
        this._canLaunch = null;
    }
    get domain() {
        if (this._domain == null && this.uri != null) {
            this._domain = bw_utils_Utils.getDomain(this.uri);
            if (this._domain === "") {
                this._domain = null;
            }
        }
        return this._domain;
    }
    get hostname() {
        if (this.match === bw_UriMatchStrategy.RegularExpression) {
            return null;
        }
        if (this._hostname == null && this.uri != null) {
            this._hostname = bw_utils_Utils.getHostname(this.uri);
            if (this._hostname === "") {
                this._hostname = null;
            }
        }
        return this._hostname;
    }
    get host() {
        if (this.match === bw_UriMatchStrategy.RegularExpression) {
            return null;
        }
        if (this._host == null && this.uri != null) {
            this._host = bw_utils_Utils.getHost(this.uri);
            if (this._host === "") {
                this._host = null;
            }
        }
        return this._host;
    }
    get hostnameOrUri() {
        return this.hostname != null ? this.hostname : this.uri;
    }
    get hostOrUri() {
        return this.host != null ? this.host : this.uri;
    }
    get isWebsite() {
        return (this.uri != null &&
            (this.uri.indexOf("http://") === 0 ||
                this.uri.indexOf("https://") === 0 ||
                (this.uri.indexOf("://") < 0 && !bw_utils_Utils.isNullOrWhitespace(bw_utils_Utils.getDomain(this.uri)))));
    }
    get canLaunch() {
        if (this._canLaunch != null) {
            return this._canLaunch;
        }
        if (this.uri != null && this.match !== bw_UriMatchStrategy.RegularExpression) {
            this._canLaunch = bw_SafeUrls.canLaunch(this.launchUri);
        }
        else {
            this._canLaunch = false;
        }
        return this._canLaunch;
    }
    get launchUri() {
        return this.uri.indexOf("://") < 0 && !bw_utils_Utils.isNullOrWhitespace(bw_utils_Utils.getDomain(this.uri))
            ? "http://" + this.uri
            : this.uri;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_LoginUriView(), obj);
    }
    matchesUri(targetUri, equivalentDomains, defaultUriMatch = null) {
        var _a;
        if (!this.uri || !targetUri) {
            return false;
        }
        let matchType = (_a = this.match) !== null && _a !== void 0 ? _a : defaultUriMatch;
        matchType !== null && matchType !== void 0 ? matchType : (matchType = bw_UriMatchStrategy.Domain);
        const targetDomain = bw_utils_Utils.getDomain(targetUri);
        const matchDomains = equivalentDomains.add(targetDomain);
        switch (matchType) {
            case bw_UriMatchStrategy.Domain:
                return this.matchesDomain(targetUri, matchDomains);
            case bw_UriMatchStrategy.Host: {
                const urlHost = bw_utils_Utils.getHost(targetUri);
                return urlHost != null && urlHost === bw_utils_Utils.getHost(this.uri);
            }
            case bw_UriMatchStrategy.Exact:
                return targetUri === this.uri;
            case bw_UriMatchStrategy.StartsWith:
                return targetUri.startsWith(this.uri);
            case bw_UriMatchStrategy.RegularExpression:
                try {
                    const regex = new RegExp(this.uri, "i");
                    return regex.test(targetUri);
                    // FIXME: Remove when updating file. Eslint update
                    // eslint-disable-next-line @typescript-eslint/no-unused-vars
                }
                catch (e) {
                    // Invalid regex
                    return false;
                }
            case bw_UriMatchStrategy.Never:
                return false;
            default:
                break;
        }
        return false;
    }
    matchesDomain(targetUri, matchDomains) {
        if (targetUri == null || this.domain == null || !matchDomains.has(this.domain)) {
            return false;
        }
        if (bw_utils_Utils.DomainMatchBlacklist.has(this.domain)) {
            const domainUrlHost = bw_utils_Utils.getHost(targetUri);
            return !bw_utils_Utils.DomainMatchBlacklist.get(this.domain).has(domainUrlHost);
        }
        return true;
    }
}

;// ../../libs/common/src/vault/models/view/login.view.ts
var bw_login_view_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_login_view_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};






class bw_LoginView extends bw_ItemView {
    constructor(l) {
        super();
        this.username = null;
        this.password = null;
        this.passwordRevisionDate = null;
        this.totp = null;
        this.uris = [];
        this.autofillOnPageLoad = null;
        this.fido2Credentials = null;
        if (!l) {
            return;
        }
        this.passwordRevisionDate = l.passwordRevisionDate;
        this.autofillOnPageLoad = l.autofillOnPageLoad;
    }
    get uri() {
        return this.hasUris ? this.uris[0].uri : null;
    }
    get maskedPassword() {
        return this.password != null ? "••••••••" : null;
    }
    get subTitle() {
        var _a;
        // if there's a passkey available, use that as a fallback
        if (bw_utils_Utils.isNullOrEmpty(this.username) && ((_a = this.fido2Credentials) === null || _a === void 0 ? void 0 : _a.length) > 0) {
            return this.fido2Credentials[0].userName;
        }
        return this.username;
    }
    get canLaunch() {
        return this.hasUris && this.uris.some((u) => u.canLaunch);
    }
    get hasTotp() {
        return !bw_utils_Utils.isNullOrWhitespace(this.totp);
    }
    get launchUri() {
        if (this.hasUris) {
            const uri = this.uris.find((u) => u.canLaunch);
            if (uri != null) {
                return uri.launchUri;
            }
        }
        return null;
    }
    get hasUris() {
        return this.uris != null && this.uris.length > 0;
    }
    get hasFido2Credentials() {
        return this.fido2Credentials != null && this.fido2Credentials.length > 0;
    }
    matchesUri(targetUri, equivalentDomains, defaultUriMatch = null) {
        if (this.uris == null) {
            return false;
        }
        return this.uris.some((uri) => uri.matchesUri(targetUri, equivalentDomains, defaultUriMatch));
    }
    static fromJSON(obj) {
        var _a;
        const passwordRevisionDate = obj.passwordRevisionDate == null ? null : new Date(obj.passwordRevisionDate);
        const uris = obj.uris.map((uri) => bw_LoginUriView.fromJSON(uri));
        const fido2Credentials = (_a = obj.fido2Credentials) === null || _a === void 0 ? void 0 : _a.map((key) => bw_Fido2CredentialView.fromJSON(key));
        return Object.assign(new bw_LoginView(), obj, {
            passwordRevisionDate,
            uris,
            fido2Credentials,
        });
    }
}
bw_login_view_decorate([
    bw_linkedFieldOption(bw_LoginLinkedId.Username, { sortPosition: 0 }),
    bw_login_view_metadata("design:type", String)
], bw_LoginView.prototype, "username", void 0);
bw_login_view_decorate([
    bw_linkedFieldOption(bw_LoginLinkedId.Password, { sortPosition: 1 }),
    bw_login_view_metadata("design:type", String)
], bw_LoginView.prototype, "password", void 0);

;// ../../libs/common/src/vault/models/view/password-history.view.ts
class bw_PasswordHistoryView {
    constructor(ph) {
        this.password = null;
        this.lastUsedDate = null;
        if (!ph) {
            return;
        }
        this.lastUsedDate = ph.lastUsedDate;
    }
    static fromJSON(obj) {
        const lastUsedDate = obj.lastUsedDate == null ? null : new Date(obj.lastUsedDate);
        return Object.assign(new bw_PasswordHistoryView(), obj, {
            lastUsedDate: lastUsedDate,
        });
    }
}

;// ../../libs/common/src/vault/models/view/secure-note.view.ts

class bw_SecureNoteView extends bw_ItemView {
    constructor(n) {
        super();
        this.type = null;
        if (!n) {
            return;
        }
        this.type = n.type;
    }
    get subTitle() {
        return null;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_SecureNoteView(), obj);
    }
}

;// ../../libs/common/src/vault/models/view/ssh-key.view.ts

class bw_SshKeyView extends bw_ItemView {
    constructor(n) {
        super();
        this.privateKey = null;
        this.publicKey = null;
        this.keyFingerprint = null;
        if (!n) {
            return;
        }
    }
    get maskedPrivateKey() {
        if (!this.privateKey || this.privateKey.length === 0) {
            return "";
        }
        let lines = this.privateKey.split("\n").filter((l) => l.trim() !== "");
        lines = lines.map((l, i) => {
            if (i === 0 || i === lines.length - 1) {
                return l;
            }
            return this.maskLine(l);
        });
        return lines.join("\n");
    }
    maskLine(line) {
        return "•".repeat(32);
    }
    get subTitle() {
        return this.keyFingerprint;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_SshKeyView(), obj);
    }
}

;// ../../libs/common/src/vault/models/view/cipher.view.ts












class bw_CipherView {
    constructor(c) {
        var _a;
        this.initializerKey = bw_InitializerKey.CipherView;
        this.id = null;
        this.organizationId = null;
        this.folderId = null;
        this.name = null;
        this.notes = null;
        this.type = null;
        this.favorite = false;
        this.organizationUseTotp = false;
        this.permissions = new bw_CipherPermissionsApi();
        this.edit = false;
        this.viewPassword = true;
        this.login = new bw_LoginView();
        this.identity = new bw_IdentityView();
        this.card = new bw_CardView();
        this.secureNote = new bw_SecureNoteView();
        this.sshKey = new bw_SshKeyView();
        this.attachments = null;
        this.fields = null;
        this.passwordHistory = null;
        this.collectionIds = null;
        this.revisionDate = null;
        this.creationDate = null;
        this.deletedDate = null;
        this.reprompt = bw_CipherRepromptType.None;
        /**
         * Flag to indicate if the cipher decryption failed.
         */
        this.decryptionFailure = false;
        if (!c) {
            return;
        }
        this.id = c.id;
        this.organizationId = c.organizationId;
        this.folderId = c.folderId;
        this.favorite = c.favorite;
        this.organizationUseTotp = c.organizationUseTotp;
        this.edit = c.edit;
        this.viewPassword = c.viewPassword;
        this.permissions = c.permissions;
        this.type = c.type;
        this.localData = c.localData;
        this.collectionIds = c.collectionIds;
        this.revisionDate = c.revisionDate;
        this.creationDate = c.creationDate;
        this.deletedDate = c.deletedDate;
        // Old locally stored ciphers might have reprompt == null. If so set it to None.
        this.reprompt = (_a = c.reprompt) !== null && _a !== void 0 ? _a : bw_CipherRepromptType.None;
    }
    get item() {
        switch (this.type) {
            case bw_CipherType.Login:
                return this.login;
            case bw_CipherType.SecureNote:
                return this.secureNote;
            case bw_CipherType.Card:
                return this.card;
            case bw_CipherType.Identity:
                return this.identity;
            case bw_CipherType.SshKey:
                return this.sshKey;
            default:
                break;
        }
        return null;
    }
    get subTitle() {
        var _a;
        return (_a = this.item) === null || _a === void 0 ? void 0 : _a.subTitle;
    }
    get hasPasswordHistory() {
        return this.passwordHistory && this.passwordHistory.length > 0;
    }
    get hasAttachments() {
        return this.attachments && this.attachments.length > 0;
    }
    get hasOldAttachments() {
        if (this.hasAttachments) {
            for (let i = 0; i < this.attachments.length; i++) {
                if (this.attachments[i].key == null) {
                    return true;
                }
            }
        }
        return false;
    }
    get hasFields() {
        return this.fields && this.fields.length > 0;
    }
    get passwordRevisionDisplayDate() {
        if (this.type !== bw_CipherType.Login || this.login == null) {
            return null;
        }
        else if (this.login.password == null || this.login.password === "") {
            return null;
        }
        return this.login.passwordRevisionDate;
    }
    get isDeleted() {
        return this.deletedDate != null;
    }
    get linkedFieldOptions() {
        var _a;
        return (_a = this.item) === null || _a === void 0 ? void 0 : _a.linkedFieldOptions;
    }
    get isUnassigned() {
        return (this.organizationId != null && (this.collectionIds == null || this.collectionIds.length === 0));
    }
    get canAssignToCollections() {
        if (this.organizationId == null) {
            return true;
        }
        return this.edit && this.viewPassword;
    }
    /**
     * Determines if the cipher can be launched in a new browser tab.
     */
    get canLaunch() {
        return this.type === bw_CipherType.Login && this.login.canLaunch;
    }
    linkedFieldValue(id) {
        var _a;
        const linkedFieldOption = (_a = this.linkedFieldOptions) === null || _a === void 0 ? void 0 : _a.get(id);
        if (linkedFieldOption == null) {
            return null;
        }
        // FIXME: Remove when updating file. Eslint update
        // eslint-disable-next-line @typescript-eslint/no-unused-vars
        const item = this.item;
        return this.item[linkedFieldOption.propertyKey];
    }
    linkedFieldI18nKey(id) {
        var _a;
        return (_a = this.linkedFieldOptions.get(id)) === null || _a === void 0 ? void 0 : _a.i18nKey;
    }
    // This is used as a marker to indicate that the cipher view object still has its prototype
    toJSON() {
        return this;
    }
    static fromJSON(obj) {
        var _a, _b, _c;
        if (obj == null) {
            return null;
        }
        const view = new bw_CipherView();
        const revisionDate = obj.revisionDate == null ? null : new Date(obj.revisionDate);
        const deletedDate = obj.deletedDate == null ? null : new Date(obj.deletedDate);
        const attachments = (_a = obj.attachments) === null || _a === void 0 ? void 0 : _a.map((a) => bw_AttachmentView.fromJSON(a));
        const fields = (_b = obj.fields) === null || _b === void 0 ? void 0 : _b.map((f) => bw_FieldView.fromJSON(f));
        const passwordHistory = (_c = obj.passwordHistory) === null || _c === void 0 ? void 0 : _c.map((ph) => bw_PasswordHistoryView.fromJSON(ph));
        Object.assign(view, obj, {
            revisionDate: revisionDate,
            deletedDate: deletedDate,
            attachments: attachments,
            fields: fields,
            passwordHistory: passwordHistory,
        });
        switch (obj.type) {
            case bw_CipherType.Card:
                view.card = bw_CardView.fromJSON(obj.card);
                break;
            case bw_CipherType.Identity:
                view.identity = bw_IdentityView.fromJSON(obj.identity);
                break;
            case bw_CipherType.Login:
                view.login = bw_LoginView.fromJSON(obj.login);
                break;
            case bw_CipherType.SecureNote:
                view.secureNote = bw_SecureNoteView.fromJSON(obj.secureNote);
                break;
            case bw_CipherType.SshKey:
                view.sshKey = bw_SshKeyView.fromJSON(obj.sshKey);
                break;
            default:
                break;
        }
        return view;
    }
}

;// ../../libs/common/src/vault/models/domain/attachment.ts
var bw_attachment_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};






class bw_Attachment extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.size = obj.size;
        this.buildDomainModel(this, obj, {
            id: null,
            url: null,
            sizeName: null,
            fileName: null,
            key: null,
        }, ["id", "url", "sizeName"]);
    }
    decrypt(orgId_1) {
        return bw_attachment_awaiter(this, arguments, void 0, function* (orgId, context = "No Cipher Context", encKey) {
            const view = yield this.decryptObj(this, new bw_AttachmentView(this), ["fileName"], orgId, encKey, "DomainType: Attachment; " + context);
            if (this.key != null) {
                view.key = yield this.decryptAttachmentKey(orgId, encKey);
            }
            return view;
        });
    }
    decryptAttachmentKey(orgId, encKey) {
        return bw_attachment_awaiter(this, void 0, void 0, function* () {
            try {
                if (encKey == null) {
                    encKey = yield this.getKeyForDecryption(orgId);
                }
                const encryptService = bw_utils_Utils.getContainerService().getEncryptService();
                const decValue = yield encryptService.decryptToBytes(this.key, encKey);
                return new bw_SymmetricCryptoKey(decValue);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                // TODO: error?
            }
        });
    }
    getKeyForDecryption(orgId) {
        return bw_attachment_awaiter(this, void 0, void 0, function* () {
            const keyService = bw_utils_Utils.getContainerService().getKeyService();
            return orgId != null
                ? yield keyService.getOrgKey(orgId)
                : yield keyService.getUserKeyWithLegacySupport();
        });
    }
    toAttachmentData() {
        const a = new bw_AttachmentData();
        a.size = this.size;
        this.buildDataModel(this, a, {
            id: null,
            url: null,
            sizeName: null,
            fileName: null,
            key: null,
        }, ["id", "url", "sizeName"]);
        return a;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const key = bw_enc_string_EncString.fromJSON(obj.key);
        const fileName = bw_enc_string_EncString.fromJSON(obj.fileName);
        return Object.assign(new bw_Attachment(), obj, {
            key,
            fileName,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/field.ts




class bw_Field extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.type = obj.type;
        this.linkedId = obj.linkedId;
        this.buildDomainModel(this, obj, {
            name: null,
            value: null,
        }, []);
    }
    decrypt(orgId, encKey) {
        return this.decryptObj(this, new bw_FieldView(this), ["name", "value"], orgId, encKey);
    }
    toFieldData() {
        const f = new bw_FieldData();
        this.buildDataModel(this, f, {
            name: null,
            value: null,
            type: null,
            linkedId: null,
        }, ["type", "linkedId"]);
        return f;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const name = bw_enc_string_EncString.fromJSON(obj.name);
        const value = bw_enc_string_EncString.fromJSON(obj.value);
        return Object.assign(new bw_Field(), obj, {
            name,
            value,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/identity.ts




class bw_Identity extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            title: null,
            firstName: null,
            middleName: null,
            lastName: null,
            address1: null,
            address2: null,
            address3: null,
            city: null,
            state: null,
            postalCode: null,
            country: null,
            company: null,
            email: null,
            phone: null,
            ssn: null,
            username: null,
            passportNumber: null,
            licenseNumber: null,
        }, []);
    }
    decrypt(orgId, context = "No Cipher Context", encKey) {
        return this.decryptObj(this, new bw_IdentityView(), [
            "title",
            "firstName",
            "middleName",
            "lastName",
            "address1",
            "address2",
            "address3",
            "city",
            "state",
            "postalCode",
            "country",
            "company",
            "email",
            "phone",
            "ssn",
            "username",
            "passportNumber",
            "licenseNumber",
        ], orgId, encKey, "DomainType: Identity; " + context);
    }
    toIdentityData() {
        const i = new bw_IdentityData();
        this.buildDataModel(this, i, {
            title: null,
            firstName: null,
            middleName: null,
            lastName: null,
            address1: null,
            address2: null,
            address3: null,
            city: null,
            state: null,
            postalCode: null,
            country: null,
            company: null,
            email: null,
            phone: null,
            ssn: null,
            username: null,
            passportNumber: null,
            licenseNumber: null,
        });
        return i;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const title = bw_enc_string_EncString.fromJSON(obj.title);
        const firstName = bw_enc_string_EncString.fromJSON(obj.firstName);
        const middleName = bw_enc_string_EncString.fromJSON(obj.middleName);
        const lastName = bw_enc_string_EncString.fromJSON(obj.lastName);
        const address1 = bw_enc_string_EncString.fromJSON(obj.address1);
        const address2 = bw_enc_string_EncString.fromJSON(obj.address2);
        const address3 = bw_enc_string_EncString.fromJSON(obj.address3);
        const city = bw_enc_string_EncString.fromJSON(obj.city);
        const state = bw_enc_string_EncString.fromJSON(obj.state);
        const postalCode = bw_enc_string_EncString.fromJSON(obj.postalCode);
        const country = bw_enc_string_EncString.fromJSON(obj.country);
        const company = bw_enc_string_EncString.fromJSON(obj.company);
        const email = bw_enc_string_EncString.fromJSON(obj.email);
        const phone = bw_enc_string_EncString.fromJSON(obj.phone);
        const ssn = bw_enc_string_EncString.fromJSON(obj.ssn);
        const username = bw_enc_string_EncString.fromJSON(obj.username);
        const passportNumber = bw_enc_string_EncString.fromJSON(obj.passportNumber);
        const licenseNumber = bw_enc_string_EncString.fromJSON(obj.licenseNumber);
        return Object.assign(new bw_Identity(), obj, {
            title,
            firstName,
            middleName,
            lastName,
            address1,
            address2,
            address3,
            city,
            state,
            postalCode,
            country,
            company,
            email,
            phone,
            ssn,
            username,
            passportNumber,
            licenseNumber,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/fido2-credential.ts
var bw_fido2_credential_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_Fido2Credential extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        this.credentialId = null;
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            credentialId: null,
            keyType: null,
            keyAlgorithm: null,
            keyCurve: null,
            keyValue: null,
            rpId: null,
            userHandle: null,
            userName: null,
            counter: null,
            rpName: null,
            userDisplayName: null,
            discoverable: null,
        }, []);
        this.creationDate = obj.creationDate != null ? new Date(obj.creationDate) : null;
    }
    decrypt(orgId, encKey) {
        return bw_fido2_credential_awaiter(this, void 0, void 0, function* () {
            const view = yield this.decryptObj(this, new bw_Fido2CredentialView(), [
                "credentialId",
                "keyType",
                "keyAlgorithm",
                "keyCurve",
                "keyValue",
                "rpId",
                "userHandle",
                "userName",
                "rpName",
                "userDisplayName",
            ], orgId, encKey);
            const { counter } = yield this.decryptObj(this, { counter: "" }, ["counter"], orgId, encKey);
            // Counter will end up as NaN if this fails
            view.counter = parseInt(counter);
            const { discoverable } = yield this.decryptObj(this, { discoverable: "" }, ["discoverable"], orgId, encKey);
            view.discoverable = discoverable === "true";
            view.creationDate = this.creationDate;
            return view;
        });
    }
    toFido2CredentialData() {
        const i = new bw_Fido2CredentialData();
        i.creationDate = this.creationDate.toISOString();
        this.buildDataModel(this, i, {
            credentialId: null,
            keyType: null,
            keyAlgorithm: null,
            keyCurve: null,
            keyValue: null,
            rpId: null,
            userHandle: null,
            userName: null,
            counter: null,
            rpName: null,
            userDisplayName: null,
            discoverable: null,
        });
        return i;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const credentialId = bw_enc_string_EncString.fromJSON(obj.credentialId);
        const keyType = bw_enc_string_EncString.fromJSON(obj.keyType);
        const keyAlgorithm = bw_enc_string_EncString.fromJSON(obj.keyAlgorithm);
        const keyCurve = bw_enc_string_EncString.fromJSON(obj.keyCurve);
        const keyValue = bw_enc_string_EncString.fromJSON(obj.keyValue);
        const rpId = bw_enc_string_EncString.fromJSON(obj.rpId);
        const userHandle = bw_enc_string_EncString.fromJSON(obj.userHandle);
        const userName = bw_enc_string_EncString.fromJSON(obj.userName);
        const counter = bw_enc_string_EncString.fromJSON(obj.counter);
        const rpName = bw_enc_string_EncString.fromJSON(obj.rpName);
        const userDisplayName = bw_enc_string_EncString.fromJSON(obj.userDisplayName);
        const discoverable = bw_enc_string_EncString.fromJSON(obj.discoverable);
        const creationDate = obj.creationDate != null ? new Date(obj.creationDate) : null;
        return Object.assign(new bw_Fido2Credential(), obj, {
            credentialId,
            keyType,
            keyAlgorithm,
            keyCurve,
            keyValue,
            rpId,
            userHandle,
            userName,
            counter,
            rpName,
            userDisplayName,
            discoverable,
            creationDate,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/login-uri.ts
var bw_login_uri_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_LoginUri extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.match = obj.match;
        this.buildDomainModel(this, obj, {
            uri: null,
            uriChecksum: null,
        }, []);
    }
    decrypt(orgId, context = "No Cipher Context", encKey) {
        return this.decryptObj(this, new bw_LoginUriView(this), ["uri"], orgId, encKey, context);
    }
    validateChecksum(clearTextUri, orgId, encKey) {
        return bw_login_uri_awaiter(this, void 0, void 0, function* () {
            if (this.uriChecksum == null) {
                return false;
            }
            const keyService = bw_utils_Utils.getContainerService().getEncryptService();
            const localChecksum = yield keyService.hash(clearTextUri, "sha256");
            const remoteChecksum = yield this.uriChecksum.decrypt(orgId, encKey);
            return remoteChecksum === localChecksum;
        });
    }
    toLoginUriData() {
        const u = new bw_LoginUriData();
        this.buildDataModel(this, u, {
            uri: null,
            uriChecksum: null,
            match: null,
        }, ["match"]);
        return u;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const uri = bw_enc_string_EncString.fromJSON(obj.uri);
        const uriChecksum = bw_enc_string_EncString.fromJSON(obj.uriChecksum);
        return Object.assign(new bw_LoginUri(), obj, {
            uri,
            uriChecksum,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/login.ts
var bw_login_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};






class bw_Login extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.passwordRevisionDate =
            obj.passwordRevisionDate != null ? new Date(obj.passwordRevisionDate) : null;
        this.autofillOnPageLoad = obj.autofillOnPageLoad;
        this.buildDomainModel(this, obj, {
            username: null,
            password: null,
            totp: null,
        }, []);
        if (obj.uris) {
            this.uris = [];
            obj.uris.forEach((u) => {
                this.uris.push(new bw_LoginUri(u));
            });
        }
        if (obj.fido2Credentials) {
            this.fido2Credentials = obj.fido2Credentials.map((key) => new bw_Fido2Credential(key));
        }
    }
    decrypt(orgId_1, bypassValidation_1) {
        return bw_login_awaiter(this, arguments, void 0, function* (orgId, bypassValidation, context = "No Cipher Context", encKey) {
            const view = yield this.decryptObj(this, new bw_LoginView(this), ["username", "password", "totp"], orgId, encKey, `DomainType: Login; ${context}`);
            if (this.uris != null) {
                view.uris = [];
                for (let i = 0; i < this.uris.length; i++) {
                    // If the uri is null, there is nothing to decrypt or validate
                    if (this.uris[i].uri == null) {
                        continue;
                    }
                    const uri = yield this.uris[i].decrypt(orgId, context, encKey);
                    // URIs are shared remotely after decryption
                    // we need to validate that the string hasn't been changed by a compromised server
                    // This validation is tied to the existence of cypher.key for backwards compatibility
                    // So we bypass the validation if there's no cipher.key or procceed with the validation and
                    // Skip the value if it's been tampered with.
                    if (bypassValidation || (yield this.uris[i].validateChecksum(uri.uri, orgId, encKey))) {
                        view.uris.push(uri);
                    }
                }
            }
            if (this.fido2Credentials != null) {
                view.fido2Credentials = yield Promise.all(this.fido2Credentials.map((key) => key.decrypt(orgId, encKey)));
            }
            return view;
        });
    }
    toLoginData() {
        const l = new bw_LoginData();
        l.passwordRevisionDate =
            this.passwordRevisionDate != null ? this.passwordRevisionDate.toISOString() : null;
        l.autofillOnPageLoad = this.autofillOnPageLoad;
        this.buildDataModel(this, l, {
            username: null,
            password: null,
            totp: null,
        });
        if (this.uris != null && this.uris.length > 0) {
            l.uris = [];
            this.uris.forEach((u) => {
                l.uris.push(u.toLoginUriData());
            });
        }
        if (this.fido2Credentials != null && this.fido2Credentials.length > 0) {
            l.fido2Credentials = this.fido2Credentials.map((key) => key.toFido2CredentialData());
        }
        return l;
    }
    static fromJSON(obj) {
        var _a, _b, _c;
        if (obj == null) {
            return null;
        }
        const username = bw_enc_string_EncString.fromJSON(obj.username);
        const password = bw_enc_string_EncString.fromJSON(obj.password);
        const totp = bw_enc_string_EncString.fromJSON(obj.totp);
        const passwordRevisionDate = obj.passwordRevisionDate == null ? null : new Date(obj.passwordRevisionDate);
        const uris = (_a = obj.uris) === null || _a === void 0 ? void 0 : _a.map((uri) => bw_LoginUri.fromJSON(uri));
        const fido2Credentials = (_c = (_b = obj.fido2Credentials) === null || _b === void 0 ? void 0 : _b.map((key) => bw_Fido2Credential.fromJSON(key))) !== null && _c !== void 0 ? _c : [];
        return Object.assign(new bw_Login(), obj, {
            username,
            password,
            totp,
            passwordRevisionDate,
            uris,
            fido2Credentials,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/password.ts




class bw_Password extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            password: null,
        });
        this.lastUsedDate = new Date(obj.lastUsedDate);
    }
    decrypt(orgId, encKey) {
        return this.decryptObj(this, new bw_PasswordHistoryView(this), ["password"], orgId, encKey, "DomainType: PasswordHistory");
    }
    toPasswordHistoryData() {
        const ph = new bw_PasswordHistoryData();
        ph.lastUsedDate = this.lastUsedDate.toISOString();
        this.buildDataModel(this, ph, {
            password: null,
        });
        return ph;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const password = bw_enc_string_EncString.fromJSON(obj.password);
        const lastUsedDate = obj.lastUsedDate == null ? null : new Date(obj.lastUsedDate);
        return Object.assign(new bw_Password(), obj, {
            password,
            lastUsedDate,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/secure-note.ts
var bw_secure_note_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_SecureNote extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.type = obj.type;
    }
    decrypt(orgId_1) {
        return bw_secure_note_awaiter(this, arguments, void 0, function* (orgId, context = "No Cipher Context", encKey) {
            return new bw_SecureNoteView(this);
        });
    }
    toSecureNoteData() {
        const n = new bw_SecureNoteData();
        n.type = this.type;
        return n;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return Object.assign(new bw_SecureNote(), obj);
    }
}

;// ../../libs/common/src/vault/models/domain/ssh-key.ts




class bw_SshKey extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            privateKey: null,
            publicKey: null,
            keyFingerprint: null,
        }, []);
    }
    decrypt(orgId, context = "No Cipher Context", encKey) {
        return this.decryptObj(this, new bw_SshKeyView(), ["privateKey", "publicKey", "keyFingerprint"], orgId, encKey, "DomainType: SshKey; " + context);
    }
    toSshKeyData() {
        const c = new bw_SshKeyData();
        this.buildDataModel(this, c, {
            privateKey: null,
            publicKey: null,
            keyFingerprint: null,
        });
        return c;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const privateKey = bw_enc_string_EncString.fromJSON(obj.privateKey);
        const publicKey = bw_enc_string_EncString.fromJSON(obj.publicKey);
        const keyFingerprint = bw_enc_string_EncString.fromJSON(obj.keyFingerprint);
        return Object.assign(new bw_SshKey(), obj, {
            privateKey,
            publicKey,
            keyFingerprint,
        });
    }
}

;// ../../libs/common/src/vault/models/domain/cipher.ts
var bw_cipher_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
















class bw_Cipher extends bw_domain_base_Domain {
    constructor(obj, localData = null) {
        super();
        this.initializerKey = bw_InitializerKey.Cipher;
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            id: null,
            organizationId: null,
            folderId: null,
            name: null,
            notes: null,
            key: null,
        }, ["id", "organizationId", "folderId"]);
        this.type = obj.type;
        this.favorite = obj.favorite;
        this.organizationUseTotp = obj.organizationUseTotp;
        this.edit = obj.edit;
        if (obj.viewPassword != null) {
            this.viewPassword = obj.viewPassword;
        }
        else {
            this.viewPassword = true; // Default for already synced Ciphers without viewPassword
        }
        this.permissions = obj.permissions;
        this.revisionDate = obj.revisionDate != null ? new Date(obj.revisionDate) : null;
        this.collectionIds = obj.collectionIds;
        this.localData = localData;
        this.creationDate = obj.creationDate != null ? new Date(obj.creationDate) : null;
        this.deletedDate = obj.deletedDate != null ? new Date(obj.deletedDate) : null;
        this.reprompt = obj.reprompt;
        switch (this.type) {
            case bw_CipherType.Login:
                this.login = new bw_Login(obj.login);
                break;
            case bw_CipherType.SecureNote:
                this.secureNote = new bw_SecureNote(obj.secureNote);
                break;
            case bw_CipherType.Card:
                this.card = new bw_Card(obj.card);
                break;
            case bw_CipherType.Identity:
                this.identity = new bw_Identity(obj.identity);
                break;
            case bw_CipherType.SshKey:
                this.sshKey = new bw_SshKey(obj.sshKey);
                break;
            default:
                break;
        }
        if (obj.attachments != null) {
            this.attachments = obj.attachments.map((a) => new bw_Attachment(a));
        }
        else {
            this.attachments = null;
        }
        if (obj.fields != null) {
            this.fields = obj.fields.map((f) => new bw_Field(f));
        }
        else {
            this.fields = null;
        }
        if (obj.passwordHistory != null) {
            this.passwordHistory = obj.passwordHistory.map((ph) => new bw_Password(ph));
        }
        else {
            this.passwordHistory = null;
        }
    }
    // We are passing the organizationId into the EncString.decrypt() method here, but because the encKey will always be
    // present and so the organizationId will not be used.
    // We will refactor the EncString.decrypt() in https://bitwarden.atlassian.net/browse/PM-3762 to remove the dependency on the organizationId.
    decrypt(encKey) {
        return bw_cipher_awaiter(this, void 0, void 0, function* () {
            const model = new bw_CipherView(this);
            let bypassValidation = true;
            if (this.key != null) {
                const encryptService = bw_utils_Utils.getContainerService().getEncryptService();
                const keyBytes = yield encryptService.decryptToBytes(this.key, encKey, `Cipher Id: ${this.id}; Content: CipherKey; IsEncryptedByOrgKey: ${this.organizationId != null}`);
                if (keyBytes == null) {
                    model.name = "[error: cannot decrypt]";
                    model.decryptionFailure = true;
                    return model;
                }
                encKey = new bw_SymmetricCryptoKey(keyBytes);
                bypassValidation = false;
            }
            yield this.decryptObj(this, model, ["name", "notes"], this.organizationId, encKey);
            switch (this.type) {
                case bw_CipherType.Login:
                    model.login = yield this.login.decrypt(this.organizationId, bypassValidation, `Cipher Id: ${this.id}`, encKey);
                    break;
                case bw_CipherType.SecureNote:
                    model.secureNote = yield this.secureNote.decrypt(this.organizationId, `Cipher Id: ${this.id}`, encKey);
                    break;
                case bw_CipherType.Card:
                    model.card = yield this.card.decrypt(this.organizationId, `Cipher Id: ${this.id}`, encKey);
                    break;
                case bw_CipherType.Identity:
                    model.identity = yield this.identity.decrypt(this.organizationId, `Cipher Id: ${this.id}`, encKey);
                    break;
                case bw_CipherType.SshKey:
                    model.sshKey = yield this.sshKey.decrypt(this.organizationId, `Cipher Id: ${this.id}`, encKey);
                    break;
                default:
                    break;
            }
            if (this.attachments != null && this.attachments.length > 0) {
                const attachments = [];
                for (const attachment of this.attachments) {
                    attachments.push(yield attachment.decrypt(this.organizationId, `Cipher Id: ${this.id}`, encKey));
                }
                model.attachments = attachments;
            }
            if (this.fields != null && this.fields.length > 0) {
                const fields = [];
                for (const field of this.fields) {
                    fields.push(yield field.decrypt(this.organizationId, encKey));
                }
                model.fields = fields;
            }
            if (this.passwordHistory != null && this.passwordHistory.length > 0) {
                const passwordHistory = [];
                for (const ph of this.passwordHistory) {
                    passwordHistory.push(yield ph.decrypt(this.organizationId, encKey));
                }
                model.passwordHistory = passwordHistory;
            }
            return model;
        });
    }
    toCipherData() {
        var _a;
        const c = new bw_CipherData();
        c.id = this.id;
        c.organizationId = this.organizationId;
        c.folderId = this.folderId;
        c.edit = this.edit;
        c.viewPassword = this.viewPassword;
        c.organizationUseTotp = this.organizationUseTotp;
        c.favorite = this.favorite;
        c.revisionDate = this.revisionDate != null ? this.revisionDate.toISOString() : null;
        c.type = this.type;
        c.collectionIds = this.collectionIds;
        c.creationDate = this.creationDate != null ? this.creationDate.toISOString() : null;
        c.deletedDate = this.deletedDate != null ? this.deletedDate.toISOString() : null;
        c.reprompt = this.reprompt;
        c.key = (_a = this.key) === null || _a === void 0 ? void 0 : _a.encryptedString;
        c.permissions = this.permissions;
        this.buildDataModel(this, c, {
            name: null,
            notes: null,
        });
        switch (c.type) {
            case bw_CipherType.Login:
                c.login = this.login.toLoginData();
                break;
            case bw_CipherType.SecureNote:
                c.secureNote = this.secureNote.toSecureNoteData();
                break;
            case bw_CipherType.Card:
                c.card = this.card.toCardData();
                break;
            case bw_CipherType.Identity:
                c.identity = this.identity.toIdentityData();
                break;
            case bw_CipherType.SshKey:
                c.sshKey = this.sshKey.toSshKeyData();
                break;
            default:
                break;
        }
        if (this.fields != null) {
            c.fields = this.fields.map((f) => f.toFieldData());
        }
        if (this.attachments != null) {
            c.attachments = this.attachments.map((a) => a.toAttachmentData());
        }
        if (this.passwordHistory != null) {
            c.passwordHistory = this.passwordHistory.map((ph) => ph.toPasswordHistoryData());
        }
        return c;
    }
    static fromJSON(obj) {
        var _a, _b, _c;
        if (obj == null) {
            return null;
        }
        const domain = new bw_Cipher();
        const name = bw_enc_string_EncString.fromJSON(obj.name);
        const notes = bw_enc_string_EncString.fromJSON(obj.notes);
        const revisionDate = obj.revisionDate == null ? null : new Date(obj.revisionDate);
        const deletedDate = obj.deletedDate == null ? null : new Date(obj.deletedDate);
        const attachments = (_a = obj.attachments) === null || _a === void 0 ? void 0 : _a.map((a) => bw_Attachment.fromJSON(a));
        const fields = (_b = obj.fields) === null || _b === void 0 ? void 0 : _b.map((f) => bw_Field.fromJSON(f));
        const passwordHistory = (_c = obj.passwordHistory) === null || _c === void 0 ? void 0 : _c.map((ph) => bw_Password.fromJSON(ph));
        const key = bw_enc_string_EncString.fromJSON(obj.key);
        Object.assign(domain, obj, {
            name,
            notes,
            revisionDate,
            deletedDate,
            attachments,
            fields,
            passwordHistory,
            key,
        });
        switch (obj.type) {
            case bw_CipherType.Card:
                domain.card = bw_Card.fromJSON(obj.card);
                break;
            case bw_CipherType.Identity:
                domain.identity = bw_Identity.fromJSON(obj.identity);
                break;
            case bw_CipherType.Login:
                domain.login = bw_Login.fromJSON(obj.login);
                break;
            case bw_CipherType.SecureNote:
                domain.secureNote = bw_SecureNote.fromJSON(obj.secureNote);
                break;
            case bw_CipherType.SshKey:
                domain.sshKey = bw_SshKey.fromJSON(obj.sshKey);
                break;
            default:
                break;
        }
        return domain;
    }
}

;// ../../libs/common/src/models/export/field.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_FieldExport {
    static template() {
        const req = new bw_FieldExport();
        req.name = "Field name";
        req.value = "Some value";
        req.type = bw_FieldType.Text;
        return req;
    }
    static toView(req, view = new bw_FieldView()) {
        view.type = req.type;
        view.value = req.value;
        view.name = req.name;
        view.linkedId = req.linkedId;
        return view;
    }
    static toDomain(req, domain = new bw_Field()) {
        domain.type = req.type;
        domain.value = req.value != null ? new bw_enc_string_EncString(req.value) : null;
        domain.name = req.name != null ? new bw_enc_string_EncString(req.name) : null;
        domain.linkedId = req.linkedId;
        return domain;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.name = bw_safeGetString(o.name);
        this.value = bw_safeGetString(o.value);
        this.type = o.type;
        this.linkedId = o.linkedId;
    }
}

;// ../../libs/common/src/models/export/identity.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_IdentityExport {
    static template() {
        const req = new bw_IdentityExport();
        req.title = "Mr";
        req.firstName = "John";
        req.middleName = "William";
        req.lastName = "Doe";
        req.address1 = "123 Any St";
        req.address2 = "Apt #123";
        req.address3 = null;
        req.city = "New York";
        req.state = "NY";
        req.postalCode = "10001";
        req.country = "US";
        req.company = "Acme Inc.";
        req.email = "john@company.com";
        req.phone = "5555551234";
        req.ssn = "000-123-4567";
        req.username = "jdoe";
        req.passportNumber = "US-123456789";
        req.licenseNumber = "D123-12-123-12333";
        return req;
    }
    static toView(req, view = new bw_IdentityView()) {
        view.title = req.title;
        view.firstName = req.firstName;
        view.middleName = req.middleName;
        view.lastName = req.lastName;
        view.address1 = req.address1;
        view.address2 = req.address2;
        view.address3 = req.address3;
        view.city = req.city;
        view.state = req.state;
        view.postalCode = req.postalCode;
        view.country = req.country;
        view.company = req.company;
        view.email = req.email;
        view.phone = req.phone;
        view.ssn = req.ssn;
        view.username = req.username;
        view.passportNumber = req.passportNumber;
        view.licenseNumber = req.licenseNumber;
        return view;
    }
    static toDomain(req, domain = new bw_Identity()) {
        domain.title = req.title != null ? new bw_enc_string_EncString(req.title) : null;
        domain.firstName = req.firstName != null ? new bw_enc_string_EncString(req.firstName) : null;
        domain.middleName = req.middleName != null ? new bw_enc_string_EncString(req.middleName) : null;
        domain.lastName = req.lastName != null ? new bw_enc_string_EncString(req.lastName) : null;
        domain.address1 = req.address1 != null ? new bw_enc_string_EncString(req.address1) : null;
        domain.address2 = req.address2 != null ? new bw_enc_string_EncString(req.address2) : null;
        domain.address3 = req.address3 != null ? new bw_enc_string_EncString(req.address3) : null;
        domain.city = req.city != null ? new bw_enc_string_EncString(req.city) : null;
        domain.state = req.state != null ? new bw_enc_string_EncString(req.state) : null;
        domain.postalCode = req.postalCode != null ? new bw_enc_string_EncString(req.postalCode) : null;
        domain.country = req.country != null ? new bw_enc_string_EncString(req.country) : null;
        domain.company = req.company != null ? new bw_enc_string_EncString(req.company) : null;
        domain.email = req.email != null ? new bw_enc_string_EncString(req.email) : null;
        domain.phone = req.phone != null ? new bw_enc_string_EncString(req.phone) : null;
        domain.ssn = req.ssn != null ? new bw_enc_string_EncString(req.ssn) : null;
        domain.username = req.username != null ? new bw_enc_string_EncString(req.username) : null;
        domain.passportNumber = req.passportNumber != null ? new bw_enc_string_EncString(req.passportNumber) : null;
        domain.licenseNumber = req.licenseNumber != null ? new bw_enc_string_EncString(req.licenseNumber) : null;
        return domain;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.title = bw_safeGetString(o.title);
        this.firstName = bw_safeGetString(o.firstName);
        this.middleName = bw_safeGetString(o.middleName);
        this.lastName = bw_safeGetString(o.lastName);
        this.address1 = bw_safeGetString(o.address1);
        this.address2 = bw_safeGetString(o.address2);
        this.address3 = bw_safeGetString(o.address3);
        this.city = bw_safeGetString(o.city);
        this.state = bw_safeGetString(o.state);
        this.postalCode = bw_safeGetString(o.postalCode);
        this.country = bw_safeGetString(o.country);
        this.company = bw_safeGetString(o.company);
        this.email = bw_safeGetString(o.email);
        this.phone = bw_safeGetString(o.phone);
        this.ssn = bw_safeGetString(o.ssn);
        this.username = bw_safeGetString(o.username);
        this.passportNumber = bw_safeGetString(o.passportNumber);
        this.licenseNumber = bw_safeGetString(o.licenseNumber);
    }
}

;// ../../libs/common/src/models/export/fido2-credential.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




/**
 * Represents format of Fido2 Credentials in JSON exports.
 */
class bw_Fido2CredentialExport {
    /**
     * Generates a template for Fido2CredentialExport
     * @returns Instance of Fido2CredentialExport with predefined values.
     */
    static template() {
        const req = new bw_Fido2CredentialExport();
        req.credentialId = "keyId";
        req.keyType = "keyType";
        req.keyAlgorithm = "keyAlgorithm";
        req.keyCurve = "keyCurve";
        req.keyValue = "keyValue";
        req.rpId = "rpId";
        req.userHandle = "userHandle";
        req.userName = "userName";
        req.counter = "counter";
        req.rpName = "rpName";
        req.userDisplayName = "userDisplayName";
        req.discoverable = "false";
        req.creationDate = null;
        return req;
    }
    /**
     * Converts a Fido2CredentialExport object to its view representation.
     * @param req - The Fido2CredentialExport object to be converted.
     * @param view - (Optional) The Fido2CredentialView object to popualte with Fido2CredentialExport data
     * @returns Fido2CredentialView - The populated view, or a new instance if none was provided.
     */
    static toView(req, view = new bw_Fido2CredentialView()) {
        view.credentialId = req.credentialId;
        view.keyType = req.keyType;
        view.keyAlgorithm = req.keyAlgorithm;
        view.keyCurve = req.keyCurve;
        view.keyValue = req.keyValue;
        view.rpId = req.rpId;
        view.userHandle = req.userHandle;
        view.userName = req.userName;
        view.counter = parseInt(req.counter);
        view.rpName = req.rpName;
        view.userDisplayName = req.userDisplayName;
        view.discoverable = req.discoverable === "true";
        view.creationDate = new Date(req.creationDate);
        return view;
    }
    /**
     * Converts a Fido2CredentialExport object to its domain representation.
     * @param req - The Fido2CredentialExport object to be converted.
     * @param domain - (Optional) The Fido2Credential object to popualte with Fido2CredentialExport data
     * @returns Fido2Credential - The populated domain, or a new instance if none was provided.
     */
    static toDomain(req, domain = new bw_Fido2Credential()) {
        domain.credentialId = req.credentialId != null ? new bw_enc_string_EncString(req.credentialId) : null;
        domain.keyType = req.keyType != null ? new bw_enc_string_EncString(req.keyType) : null;
        domain.keyAlgorithm = req.keyAlgorithm != null ? new bw_enc_string_EncString(req.keyAlgorithm) : null;
        domain.keyCurve = req.keyCurve != null ? new bw_enc_string_EncString(req.keyCurve) : null;
        domain.keyValue = req.keyValue != null ? new bw_enc_string_EncString(req.keyValue) : null;
        domain.rpId = req.rpId != null ? new bw_enc_string_EncString(req.rpId) : null;
        domain.userHandle = req.userHandle != null ? new bw_enc_string_EncString(req.userHandle) : null;
        domain.userName = req.userName != null ? new bw_enc_string_EncString(req.userName) : null;
        domain.counter = req.counter != null ? new bw_enc_string_EncString(req.counter) : null;
        domain.rpName = req.rpName != null ? new bw_enc_string_EncString(req.rpName) : null;
        domain.userDisplayName =
            req.userDisplayName != null ? new bw_enc_string_EncString(req.userDisplayName) : null;
        domain.discoverable = req.discoverable != null ? new bw_enc_string_EncString(req.discoverable) : null;
        domain.creationDate = req.creationDate;
        return domain;
    }
    /**
     * Constructs a new Fid2CredentialExport instance.
     *
     * @param o - The credential storing the data being exported. When not provided, an empty export is created instead.
     */
    constructor(o) {
        if (o == null) {
            return;
        }
        this.credentialId = bw_safeGetString(o.credentialId);
        this.keyType = bw_safeGetString(o.keyType);
        this.keyAlgorithm = bw_safeGetString(o.keyAlgorithm);
        this.keyCurve = bw_safeGetString(o.keyCurve);
        this.keyValue = bw_safeGetString(o.keyValue);
        this.rpId = bw_safeGetString(o.rpId);
        this.userHandle = bw_safeGetString(o.userHandle);
        this.userName = bw_safeGetString(o.userName);
        this.counter = bw_safeGetString(String(o.counter));
        this.rpName = bw_safeGetString(o.rpName);
        this.userDisplayName = bw_safeGetString(o.userDisplayName);
        this.discoverable = bw_safeGetString(String(o.discoverable));
        this.creationDate = o.creationDate;
    }
}

;// ../../libs/common/src/models/export/login-uri.export.ts




class bw_LoginUriExport {
    static template() {
        const req = new bw_LoginUriExport();
        req.uri = "https://google.com";
        req.match = null;
        return req;
    }
    static toView(req, view = new bw_LoginUriView()) {
        view.uri = req.uri;
        view.match = req.match;
        return view;
    }
    static toDomain(req, domain = new bw_LoginUri()) {
        domain.uri = req.uri != null ? new bw_enc_string_EncString(req.uri) : null;
        domain.uriChecksum = req.uriChecksum != null ? new bw_enc_string_EncString(req.uriChecksum) : null;
        domain.match = req.match;
        return domain;
    }
    constructor(o) {
        var _a;
        this.match = null;
        if (o == null) {
            return;
        }
        this.uri = bw_safeGetString(o.uri);
        if ("uriChecksum" in o) {
            this.uriChecksum = (_a = o.uriChecksum) === null || _a === void 0 ? void 0 : _a.encryptedString;
        }
        this.match = o.match;
    }
}

;// ../../libs/common/src/models/export/login.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






class bw_LoginExport {
    static template() {
        const req = new bw_LoginExport();
        req.uris = [];
        req.username = "jdoe";
        req.password = "myp@ssword123";
        req.totp = "JBSWY3DPEHPK3PXP";
        req.fido2Credentials = [bw_Fido2CredentialExport.template()];
        return req;
    }
    static toView(req, view = new bw_LoginView()) {
        if (req.uris != null) {
            view.uris = req.uris.map((u) => bw_LoginUriExport.toView(u));
        }
        view.username = req.username;
        view.password = req.password;
        view.totp = req.totp;
        if (req.fido2Credentials != null) {
            view.fido2Credentials = req.fido2Credentials.map((key) => bw_Fido2CredentialExport.toView(key));
        }
        return view;
    }
    static toDomain(req, domain = new bw_Login()) {
        if (req.uris != null) {
            domain.uris = req.uris.map((u) => bw_LoginUriExport.toDomain(u));
        }
        domain.username = req.username != null ? new bw_enc_string_EncString(req.username) : null;
        domain.password = req.password != null ? new bw_enc_string_EncString(req.password) : null;
        domain.totp = req.totp != null ? new bw_enc_string_EncString(req.totp) : null;
        // Fido2credentials are currently not supported for exports.
        return domain;
    }
    constructor(o) {
        this.fido2Credentials = [];
        if (o == null) {
            return;
        }
        if (o.uris != null) {
            this.uris = o.uris.map((u) => new bw_LoginUriExport(u));
        }
        if (o.fido2Credentials != null) {
            this.fido2Credentials = o.fido2Credentials.map((key) => new bw_Fido2CredentialExport(key));
        }
        this.username = bw_safeGetString(o.username);
        this.password = bw_safeGetString(o.password);
        this.totp = bw_safeGetString(o.totp);
    }
}

;// ../../libs/common/src/models/export/password-history.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_PasswordHistoryExport {
    static template() {
        const req = new bw_PasswordHistoryExport();
        req.password = null;
        req.lastUsedDate = null;
        return req;
    }
    static toView(req, view = new bw_PasswordHistoryView()) {
        view.password = req.password;
        view.lastUsedDate = req.lastUsedDate;
        return view;
    }
    static toDomain(req, domain = new bw_Password()) {
        domain.password = req.password != null ? new bw_enc_string_EncString(req.password) : null;
        domain.lastUsedDate = req.lastUsedDate;
        return domain;
    }
    constructor(o) {
        this.lastUsedDate = null;
        if (o == null) {
            return;
        }
        this.password = bw_safeGetString(o.password);
        this.lastUsedDate = o.lastUsedDate;
    }
}

;// ../../libs/common/src/models/export/secure-note.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_SecureNoteExport {
    static template() {
        const req = new bw_SecureNoteExport();
        req.type = bw_SecureNoteType.Generic;
        return req;
    }
    static toView(req, view = new bw_SecureNoteView()) {
        view.type = req.type;
        return view;
    }
    static toDomain(req, view = new bw_SecureNote()) {
        view.type = req.type;
        return view;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.type = o.type;
    }
}

// EXTERNAL MODULE: ../../node_modules/@bitwarden/sdk-internal/bitwarden_wasm_internal_bg.js
var bw_bitwarden_wasm_internal_bg = __webpack_require__(414);
;// ../../libs/common/src/models/export/ssh-key.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_SshKeyExport {
    static template() {
        const req = new bw_SshKeyExport();
        req.privateKey = "";
        req.publicKey = "";
        req.keyFingerprint = "";
        return req;
    }
    static toView(req, view = new bw_SshKeyView()) {
        const parsedKey = (0,bw_bitwarden_wasm_internal_bg/* import_ssh_key */.bn)(req.privateKey);
        view.privateKey = parsedKey.privateKey;
        view.publicKey = parsedKey.publicKey;
        view.keyFingerprint = parsedKey.fingerprint;
        return view;
    }
    static toDomain(req, domain = new bw_SshKey()) {
        domain.privateKey = new bw_enc_string_EncString(req.privateKey);
        domain.publicKey = new bw_enc_string_EncString(req.publicKey);
        domain.keyFingerprint = new bw_enc_string_EncString(req.keyFingerprint);
        return domain;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.privateKey = bw_safeGetString(o.privateKey);
        this.publicKey = bw_safeGetString(o.publicKey);
        this.keyFingerprint = bw_safeGetString(o.keyFingerprint);
    }
}

;// ../../libs/common/src/models/export/cipher.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore













class bw_CipherExport {
    constructor() {
        this.passwordHistory = null;
        this.revisionDate = null;
        this.creationDate = null;
        this.deletedDate = null;
    }
    static template() {
        const req = new bw_CipherExport();
        req.organizationId = null;
        req.collectionIds = null;
        req.folderId = null;
        req.type = bw_CipherType.Login;
        req.name = "Item name";
        req.notes = "Some notes about this item.";
        req.favorite = false;
        req.fields = [];
        req.login = null;
        req.secureNote = null;
        req.card = null;
        req.identity = null;
        req.sshKey = null;
        req.reprompt = bw_CipherRepromptType.None;
        req.passwordHistory = [];
        req.creationDate = null;
        req.revisionDate = null;
        req.deletedDate = null;
        return req;
    }
    static toView(req, view = new bw_CipherView()) {
        var _a, _b, _c;
        view.type = req.type;
        view.folderId = req.folderId;
        if (view.organizationId == null) {
            view.organizationId = req.organizationId;
        }
        if (view.collectionIds || req.collectionIds) {
            const set = new Set(((_a = view.collectionIds) !== null && _a !== void 0 ? _a : []).concat((_b = req.collectionIds) !== null && _b !== void 0 ? _b : []));
            view.collectionIds = Array.from(set.values());
        }
        view.name = req.name;
        view.notes = req.notes;
        view.favorite = req.favorite;
        view.reprompt = (_c = req.reprompt) !== null && _c !== void 0 ? _c : bw_CipherRepromptType.None;
        if (req.fields != null) {
            view.fields = req.fields.map((f) => bw_FieldExport.toView(f));
        }
        switch (req.type) {
            case bw_CipherType.Login:
                view.login = bw_LoginExport.toView(req.login);
                break;
            case bw_CipherType.SecureNote:
                view.secureNote = bw_SecureNoteExport.toView(req.secureNote);
                break;
            case bw_CipherType.Card:
                view.card = bw_CardExport.toView(req.card);
                break;
            case bw_CipherType.Identity:
                view.identity = bw_IdentityExport.toView(req.identity);
                break;
            case bw_CipherType.SshKey:
                view.sshKey = bw_SshKeyExport.toView(req.sshKey);
                break;
        }
        if (req.passwordHistory != null) {
            view.passwordHistory = req.passwordHistory.map((ph) => bw_PasswordHistoryExport.toView(ph));
        }
        view.creationDate = req.creationDate;
        view.revisionDate = req.revisionDate;
        view.deletedDate = req.deletedDate;
        return view;
    }
    static toDomain(req, domain = new bw_Cipher()) {
        var _a;
        domain.type = req.type;
        domain.folderId = req.folderId;
        if (domain.organizationId == null) {
            domain.organizationId = req.organizationId;
        }
        domain.name = req.name != null ? new bw_enc_string_EncString(req.name) : null;
        domain.notes = req.notes != null ? new bw_enc_string_EncString(req.notes) : null;
        domain.favorite = req.favorite;
        domain.reprompt = (_a = req.reprompt) !== null && _a !== void 0 ? _a : bw_CipherRepromptType.None;
        domain.key = req.key != null ? new bw_enc_string_EncString(req.key) : null;
        if (req.fields != null) {
            domain.fields = req.fields.map((f) => bw_FieldExport.toDomain(f));
        }
        switch (req.type) {
            case bw_CipherType.Login:
                domain.login = bw_LoginExport.toDomain(req.login);
                break;
            case bw_CipherType.SecureNote:
                domain.secureNote = bw_SecureNoteExport.toDomain(req.secureNote);
                break;
            case bw_CipherType.Card:
                domain.card = bw_CardExport.toDomain(req.card);
                break;
            case bw_CipherType.Identity:
                domain.identity = bw_IdentityExport.toDomain(req.identity);
                break;
            case bw_CipherType.SshKey:
                domain.sshKey = bw_SshKeyExport.toDomain(req.sshKey);
                break;
        }
        if (req.passwordHistory != null) {
            domain.passwordHistory = req.passwordHistory.map((ph) => bw_PasswordHistoryExport.toDomain(ph));
        }
        domain.creationDate = req.creationDate;
        domain.revisionDate = req.revisionDate;
        domain.deletedDate = req.deletedDate;
        return domain;
    }
    // Use build method instead of ctor so that we can control order of JSON stringify for pretty print
    build(o) {
        var _a;
        this.organizationId = o.organizationId;
        this.folderId = o.folderId;
        this.type = o.type;
        this.reprompt = o.reprompt;
        this.name = bw_safeGetString(o.name);
        this.notes = bw_safeGetString(o.notes);
        if ("key" in o) {
            this.key = (_a = o.key) === null || _a === void 0 ? void 0 : _a.encryptedString;
        }
        this.favorite = o.favorite;
        if (o.fields != null) {
            this.fields = o.fields.map((f) => new bw_FieldExport(f));
        }
        switch (o.type) {
            case bw_CipherType.Login:
                this.login = new bw_LoginExport(o.login);
                break;
            case bw_CipherType.SecureNote:
                this.secureNote = new bw_SecureNoteExport(o.secureNote);
                break;
            case bw_CipherType.Card:
                this.card = new bw_CardExport(o.card);
                break;
            case bw_CipherType.Identity:
                this.identity = new bw_IdentityExport(o.identity);
                break;
            case bw_CipherType.SshKey:
                this.sshKey = new bw_SshKeyExport(o.sshKey);
                break;
        }
        if (o.passwordHistory != null) {
            this.passwordHistory = o.passwordHistory.map((ph) => new bw_PasswordHistoryExport(ph));
        }
        this.creationDate = o.creationDate;
        this.revisionDate = o.revisionDate;
        this.deletedDate = o.deletedDate;
    }
}

;// ../../libs/common/src/models/export/collection.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_CollectionExport {
    static template() {
        const req = new bw_CollectionExport();
        req.organizationId = "00000000-0000-0000-0000-000000000000";
        req.name = "Collection name";
        req.externalId = null;
        return req;
    }
    static toView(req, view = new bw_CollectionView()) {
        view.name = req.name;
        view.externalId = req.externalId;
        if (view.organizationId == null) {
            view.organizationId = req.organizationId;
        }
        return view;
    }
    static toDomain(req, domain = new bw_Collection()) {
        domain.name = req.name != null ? new bw_enc_string_EncString(req.name) : null;
        domain.externalId = req.externalId;
        if (domain.organizationId == null) {
            domain.organizationId = req.organizationId;
        }
        return domain;
    }
    // Use build method instead of ctor so that we can control order of JSON stringify for pretty print
    build(o) {
        this.organizationId = o.organizationId;
        this.name = bw_safeGetString(o.name);
        this.externalId = o.externalId;
    }
}

;// ../../libs/common/src/vault/models/view/folder.view.ts
class bw_FolderView {
    constructor(f) {
        this.id = null;
        this.name = null;
        this.revisionDate = null;
        if (!f) {
            return;
        }
        this.id = f.id;
        this.revisionDate = f.revisionDate;
    }
    static fromJSON(obj) {
        const revisionDate = obj.revisionDate == null ? null : new Date(obj.revisionDate);
        return Object.assign(new bw_FolderView(), obj, { revisionDate });
    }
}

;// ../../libs/common/src/vault/models/domain/folder.ts
var bw_folder_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_Test extends (/* unused pure expression or super */ null && (Domain)) {
}
class bw_Folder extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            id: null,
            name: null,
        }, ["id"]);
        this.revisionDate = obj.revisionDate != null ? new Date(obj.revisionDate) : null;
    }
    decrypt() {
        return this.decryptObj(this, new bw_FolderView(this), ["name"], null);
    }
    decryptWithKey(key, encryptService) {
        return bw_folder_awaiter(this, void 0, void 0, function* () {
            const decrypted = yield this.decryptObjWithKey(["name"], key, encryptService, bw_Folder);
            const view = new bw_FolderView(decrypted);
            view.name = decrypted.name;
            return view;
        });
    }
    static fromJSON(obj) {
        const revisionDate = obj.revisionDate == null ? null : new Date(obj.revisionDate);
        return Object.assign(new bw_Folder(), obj, { name: bw_enc_string_EncString.fromJSON(obj.name), revisionDate });
    }
}

;// ../../libs/common/src/models/export/folder.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_FolderExport {
    static template() {
        const req = new bw_FolderExport();
        req.name = "Folder name";
        return req;
    }
    static toView(req, view = new bw_FolderView()) {
        view.name = req.name;
        return view;
    }
    static toDomain(req, domain = new bw_Folder()) {
        domain.name = req.name != null ? new bw_enc_string_EncString(req.name) : null;
        return domain;
    }
    // Use build method instead of ctor so that we can control order of JSON stringify for pretty print
    build(o) {
        this.name = bw_safeGetString(o.name);
    }
}

;// ./src/admin-console/models/selection-read-only.ts
class bw_SelectionReadOnly {
    static template() {
        return new bw_SelectionReadOnly("00000000-0000-0000-0000-000000000000", false, false, false);
    }
    constructor(id, readOnly, hidePasswords, manage) {
        this.id = id;
        this.readOnly = readOnly;
        this.hidePasswords = hidePasswords || false;
        this.manage = manage;
    }
}

;// ./src/admin-console/models/request/organization-collection.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_OrganizationCollectionRequest extends bw_CollectionExport {
    static template() {
        const req = new bw_OrganizationCollectionRequest();
        req.organizationId = "00000000-0000-0000-0000-000000000000";
        req.name = "Collection name";
        req.externalId = null;
        req.groups = [bw_SelectionReadOnly.template(), bw_SelectionReadOnly.template()];
        req.users = [bw_SelectionReadOnly.template(), bw_SelectionReadOnly.template()];
        return req;
    }
}

;// ../../libs/common/src/models/export/collection-with-id.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_CollectionWithIdExport extends bw_CollectionExport {
    static toView(req, view = new bw_CollectionView()) {
        view.id = req.id;
        return super.toView(req, view);
    }
    static toDomain(req, domain = new bw_Collection()) {
        domain.id = req.id;
        return super.toDomain(req, domain);
    }
    // Use build method instead of ctor so that we can control order of JSON stringify for pretty print
    build(o) {
        this.id = o.id;
        super.build(o);
    }
}

;// ./src/admin-console/models/response/collection.response.ts

class bw_collection_response_CollectionResponse extends bw_CollectionWithIdExport {
    constructor(o) {
        super();
        this.object = "collection";
        this.build(o);
    }
}

;// ./src/admin-console/models/response/organization-collection.response.ts

class bw_OrganizationCollectionResponse extends bw_collection_response_CollectionResponse {
    constructor(o, groups, users) {
        super(o);
        this.object = "org-collection";
        this.groups = groups;
        this.users = users;
    }
}

;// ./src/admin-console/models/response/organization.response.ts
class bw_OrganizationResponse {
    constructor(o) {
        this.object = "organization";
        this.id = o.id;
        this.name = o.name;
        this.status = o.status;
        this.type = o.type;
        this.enabled = o.enabled;
    }
}

;// ../../libs/common/src/tools/send/models/view/send-file.view.ts
class bw_SendFileView {
    constructor(f) {
        this.id = null;
        this.size = null;
        this.sizeName = null;
        this.fileName = null;
        if (!f) {
            return;
        }
        this.id = f.id;
        this.size = f.size;
        this.sizeName = f.sizeName;
    }
    get fileSize() {
        try {
            if (this.size != null) {
                return parseInt(this.size, null);
            }
        }
        catch (_a) {
            // Invalid file size.
        }
        return 0;
    }
    static fromJSON(json) {
        if (json == null) {
            return null;
        }
        return Object.assign(new bw_SendFileView(), json);
    }
}

;// ../../libs/common/src/tools/send/models/view/send-text.view.ts
class bw_SendTextView {
    constructor(t) {
        this.text = null;
        if (!t) {
            return;
        }
        this.hidden = t.hidden;
    }
    get maskedText() {
        return this.text != null ? "••••••••" : null;
    }
    static fromJSON(json) {
        if (json == null) {
            return null;
        }
        return Object.assign(new bw_SendTextView(), json);
    }
}

;// ../../libs/common/src/tools/send/models/view/send.view.ts




class bw_SendView {
    constructor(s) {
        this.id = null;
        this.accessId = null;
        this.name = null;
        this.notes = null;
        this.type = null;
        this.text = new bw_SendTextView();
        this.file = new bw_SendFileView();
        this.maxAccessCount = null;
        this.accessCount = 0;
        this.revisionDate = null;
        this.deletionDate = null;
        this.expirationDate = null;
        this.password = null;
        this.disabled = false;
        this.hideEmail = false;
        if (!s) {
            return;
        }
        this.id = s.id;
        this.accessId = s.accessId;
        this.type = s.type;
        this.maxAccessCount = s.maxAccessCount;
        this.accessCount = s.accessCount;
        this.revisionDate = s.revisionDate;
        this.deletionDate = s.deletionDate;
        this.expirationDate = s.expirationDate;
        this.disabled = s.disabled;
        this.password = s.password;
        this.hideEmail = s.hideEmail;
    }
    get urlB64Key() {
        return bw_utils_Utils.fromBufferToUrlB64(this.key);
    }
    get maxAccessCountReached() {
        if (this.maxAccessCount == null) {
            return false;
        }
        return this.accessCount >= this.maxAccessCount;
    }
    get expired() {
        if (this.expirationDate == null) {
            return false;
        }
        return this.expirationDate <= new Date();
    }
    get pendingDelete() {
        return this.deletionDate <= new Date();
    }
    toJSON() {
        return bw_utils_Utils.merge(Object.assign({}, this), {
            key: bw_utils_Utils.fromBufferToB64(this.key),
        });
    }
    static fromJSON(json) {
        if (json == null) {
            return null;
        }
        return Object.assign(new bw_SendView(), json, {
            key: bw_utils_Utils.fromB64ToArray(json.key),
            cryptoKey: bw_SymmetricCryptoKey.fromJSON(json.cryptoKey),
            text: bw_SendTextView.fromJSON(json.text),
            file: bw_SendFileView.fromJSON(json.file),
            revisionDate: json.revisionDate == null ? null : new Date(json.revisionDate),
            deletionDate: json.deletionDate == null ? null : new Date(json.deletionDate),
            expirationDate: json.expirationDate == null ? null : new Date(json.expirationDate),
        });
    }
}

;// ./src/tools/send/models/send-file.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SendFileResponse {
    static template(fileName = "file attachment location") {
        const req = new bw_SendFileResponse();
        req.fileName = fileName;
        return req;
    }
    static toView(file, view = new bw_SendFileView()) {
        if (file == null) {
            return null;
        }
        view.id = file.id;
        view.size = file.size;
        view.sizeName = file.sizeName;
        view.fileName = file.fileName;
        return view;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.id = o.id;
        this.size = o.size;
        this.sizeName = o.sizeName;
        this.fileName = o.fileName;
    }
}

;// ./src/tools/send/models/send-text.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SendTextResponse {
    static template(text = "Text contained in the send.", hidden = false) {
        const req = new bw_SendTextResponse();
        req.text = text;
        req.hidden = hidden;
        return req;
    }
    static toView(text, view = new bw_SendTextView()) {
        if (text == null) {
            return null;
        }
        view.text = text.text;
        view.hidden = text.hidden;
        return view;
    }
    constructor(o) {
        if (o == null) {
            return;
        }
        this.text = o.text;
        this.hidden = o.hidden;
    }
}

;// ./src/tools/send/models/send.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





const bw_dateProperties = [
    bw_utils_Utils.nameOf("deletionDate"),
    bw_utils_Utils.nameOf("expirationDate"),
];
class bw_SendResponse {
    static template(sendType, deleteInDays = 7) {
        const req = new bw_SendResponse();
        req.name = "Send name";
        req.notes = "Some notes about this send.";
        req.type = sendType === bw_SendType.File ? bw_SendType.File : bw_SendType.Text;
        req.text = sendType === bw_SendType.Text ? bw_SendTextResponse.template() : null;
        req.file = sendType === bw_SendType.File ? bw_SendFileResponse.template() : null;
        req.maxAccessCount = null;
        req.deletionDate = this.getStandardDeletionDate(deleteInDays);
        req.expirationDate = null;
        req.password = null;
        req.disabled = false;
        req.hideEmail = false;
        return req;
    }
    static toView(send, view = new bw_SendView()) {
        if (send == null) {
            return null;
        }
        view.id = send.id;
        view.accessId = send.accessId;
        view.name = send.name;
        view.notes = send.notes;
        view.key = send.key == null ? null : bw_utils_Utils.fromB64ToArray(send.key);
        view.type = send.type;
        view.file = bw_SendFileResponse.toView(send.file);
        view.text = bw_SendTextResponse.toView(send.text);
        view.maxAccessCount = send.maxAccessCount;
        view.accessCount = send.accessCount;
        view.revisionDate = send.revisionDate;
        view.deletionDate = send.deletionDate;
        view.expirationDate = send.expirationDate;
        view.password = send.password;
        view.disabled = send.disabled;
        view.hideEmail = send.hideEmail;
        return view;
    }
    static fromJson(json) {
        return JSON.parse(json, (key, value) => {
            if (bw_dateProperties.includes(key)) {
                return value == null ? null : new Date(value);
            }
            return value;
        });
    }
    static getStandardDeletionDate(days) {
        const d = new Date();
        d.setTime(d.getTime() + days * 86400000); // ms per day
        return d;
    }
    constructor(o, webVaultUrl) {
        this.object = "send";
        if (o == null) {
            return;
        }
        this.id = o.id;
        this.accessId = o.accessId;
        let sendLinkBaseUrl = webVaultUrl;
        if (sendLinkBaseUrl == null) {
            sendLinkBaseUrl = "https://send.bitwarden.com/#";
        }
        else {
            sendLinkBaseUrl += "/#/send/";
        }
        this.accessUrl = sendLinkBaseUrl + this.accessId + "/" + o.urlB64Key;
        this.name = o.name;
        this.notes = o.notes;
        this.key = bw_utils_Utils.fromBufferToB64(o.key);
        this.type = o.type;
        this.maxAccessCount = o.maxAccessCount;
        this.accessCount = o.accessCount;
        this.revisionDate = o.revisionDate;
        this.deletionDate = o.deletionDate;
        this.expirationDate = o.expirationDate;
        this.passwordSet = o.password != null;
        this.disabled = o.disabled;
        this.hideEmail = o.hideEmail;
        if (o.type === bw_SendType.Text && o.text != null) {
            this.text = new bw_SendTextResponse(o.text);
        }
        if (o.type === bw_SendType.File && o.file != null) {
            this.file = new bw_SendFileResponse(o.file);
        }
    }
}

;// ../../libs/common/src/models/export/cipher-with-ids.export.ts

class bw_CipherWithIdExport extends bw_CipherExport {
    // Use build method instead of ctor so that we can control order of JSON stringify for pretty print
    build(o) {
        this.id = o.id;
        super.build(o);
        this.collectionIds = o.collectionIds;
    }
}

;// ./src/models/response/login.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_LoginResponse extends bw_LoginExport {
    constructor(o) {
        super(o);
        this.passwordRevisionDate = o.passwordRevisionDate != null ? o.passwordRevisionDate : null;
    }
}

;// ./src/vault/models/attachment.response.ts
class bw_AttachmentResponse {
    constructor(o) {
        this.id = o.id;
        this.fileName = o.fileName;
        this.size = o.size;
        this.sizeName = o.sizeName;
        this.url = o.url;
    }
}

;// ./src/vault/models/password-history.response.ts
class bw_PasswordHistoryResponse {
    constructor(o) {
        this.lastUsedDate = o.lastUsedDate;
        this.password = o.password;
    }
}

;// ./src/vault/models/cipher.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_CipherResponse extends bw_CipherWithIdExport {
    constructor(o) {
        super();
        this.object = "item";
        this.build(o);
        if (o.attachments != null) {
            this.attachments = o.attachments.map((a) => new bw_AttachmentResponse(a));
        }
        this.revisionDate = o.revisionDate;
        if (o.creationDate != null) {
            this.creationDate = o.creationDate;
        }
        this.deletedDate = o.deletedDate;
        if (o.passwordHistory != null) {
            this.passwordHistory = o.passwordHistory.map((h) => new bw_PasswordHistoryResponse(h));
        }
        if (o.type === bw_CipherType.Login && o.login != null) {
            this.login = new bw_LoginResponse(o.login);
        }
    }
}

;// ../../libs/common/src/models/export/folder-with-id.export.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_FolderWithIdExport extends bw_FolderExport {
    static toView(req, view = new bw_FolderView()) {
        view.id = req.id;
        return super.toView(req, view);
    }
    static toDomain(req, domain = new bw_Folder()) {
        domain.id = req.id;
        return super.toDomain(req, domain);
    }
    // Use build method instead of ctor so that we can control order of JSON stringify for pretty print
    build(o) {
        this.id = o.id;
        super.build(o);
    }
}

;// ../../libs/common/src/models/export/index.ts













;// ./src/vault/models/folder.response.ts

class bw_FolderResponse extends bw_FolderWithIdExport {
    constructor(o) {
        super();
        this.object = "folder";
        this.build(o);
    }
}

;// ../../libs/common/src/platform/models/domain/enc-array-buffer.ts
var bw_enc_array_buffer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


const bw_ENC_TYPE_LENGTH = 1;
const bw_IV_LENGTH = 16;
const bw_MAC_LENGTH = 32;
const bw_MIN_DATA_LENGTH = 1;
class bw_EncArrayBuffer {
    constructor(buffer) {
        this.buffer = buffer;
        this.encryptionType = null;
        this.dataBytes = null;
        this.ivBytes = null;
        this.macBytes = null;
        const encBytes = buffer;
        const encType = encBytes[0];
        switch (encType) {
            case bw_EncryptionType.AesCbc256_HmacSha256_B64: {
                const minimumLength = bw_ENC_TYPE_LENGTH + bw_IV_LENGTH + bw_MAC_LENGTH + bw_MIN_DATA_LENGTH;
                if (encBytes.length < minimumLength) {
                    this.throwDecryptionError();
                }
                this.ivBytes = encBytes.slice(bw_ENC_TYPE_LENGTH, bw_ENC_TYPE_LENGTH + bw_IV_LENGTH);
                this.macBytes = encBytes.slice(bw_ENC_TYPE_LENGTH + bw_IV_LENGTH, bw_ENC_TYPE_LENGTH + bw_IV_LENGTH + bw_MAC_LENGTH);
                this.dataBytes = encBytes.slice(bw_ENC_TYPE_LENGTH + bw_IV_LENGTH + bw_MAC_LENGTH);
                break;
            }
            case bw_EncryptionType.AesCbc256_B64: {
                const minimumLength = bw_ENC_TYPE_LENGTH + bw_IV_LENGTH + bw_MIN_DATA_LENGTH;
                if (encBytes.length < minimumLength) {
                    this.throwDecryptionError();
                }
                this.ivBytes = encBytes.slice(bw_ENC_TYPE_LENGTH, bw_ENC_TYPE_LENGTH + bw_IV_LENGTH);
                this.dataBytes = encBytes.slice(bw_ENC_TYPE_LENGTH + bw_IV_LENGTH);
                break;
            }
            default:
                this.throwDecryptionError();
        }
        this.encryptionType = encType;
    }
    throwDecryptionError() {
        throw new Error("Error parsing encrypted ArrayBuffer: data is corrupted or has an invalid format.");
    }
    static fromResponse(response) {
        return bw_enc_array_buffer_awaiter(this, void 0, void 0, function* () {
            const buffer = yield response.arrayBuffer();
            if (buffer == null) {
                throw new Error("Cannot create EncArrayBuffer from Response - Response is empty");
            }
            return new bw_EncArrayBuffer(new Uint8Array(buffer));
        });
    }
    static fromB64(b64) {
        const buffer = bw_utils_Utils.fromB64ToArray(b64);
        return new bw_EncArrayBuffer(buffer);
    }
}

;// ./src/models/response/file.response.ts
class bw_FileResponse {
    constructor(data, fileName) {
        this.object = "file";
        this.data = data;
        this.fileName = fileName;
    }
}

;// ./src/commands/download.command.ts
var bw_download_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




/**
 * Used to download and save attachments
 */
class bw_DownloadCommand {
    /**
     * @param encryptService - Needed for decryption of the retrieved attachment
     * @param apiService - Needed to override the existing nativeFetch which is available as of Node 18, to support proxies
     */
    constructor(encryptService, apiService) {
        this.encryptService = encryptService;
        this.apiService = apiService;
    }
    /**
     * Fetches an attachment via the url, decrypts it's content and saves it to a file
     * @param url - url used to retrieve the attachment
     * @param key - SymmetricCryptoKey to decrypt the file contents
     * @param fileName - filename used when written to disk
     * @param output - If output is empty or `--raw` was passed to the initial command the content is output onto stdout
     * @returns Promise<FileResponse>
     */
    saveAttachmentToFile(url, key, fileName, output) {
        return bw_download_command_awaiter(this, void 0, void 0, function* () {
            const response = yield this.apiService.nativeFetch(new Request(url, { headers: { cache: "no-cache" } }));
            if (response.status !== 200) {
                return bw_Response.error("A " + response.status + " error occurred while downloading the attachment.");
            }
            try {
                const encBuf = yield bw_EncArrayBuffer.fromResponse(response);
                const decBuf = yield this.encryptService.decryptToBytes(encBuf, key);
                if (process.env.BW_SERVE === "true") {
                    const res = new bw_FileResponse(Buffer.from(decBuf), fileName);
                    return bw_Response.success(res);
                }
                else {
                    return yield bw_CliUtils.saveResultToFile(Buffer.from(decBuf), output, fileName);
                }
            }
            catch (e) {
                if (typeof e === "string") {
                    return bw_Response.error(e);
                }
                else {
                    return bw_Response.error("An error occurred while saving the attachment.");
                }
            }
        });
    }
}

;// ./src/commands/get.command.ts
var bw_get_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore































class bw_GetCommand extends bw_DownloadCommand {
    constructor(cipherService, folderService, collectionService, totpService, auditService, keyService, encryptService, searchService, apiService, organizationService, eventCollectionService, accountProfileService, accountService) {
        super(encryptService, apiService);
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.collectionService = collectionService;
        this.totpService = totpService;
        this.auditService = auditService;
        this.keyService = keyService;
        this.searchService = searchService;
        this.apiService = apiService;
        this.organizationService = organizationService;
        this.eventCollectionService = eventCollectionService;
        this.accountProfileService = accountProfileService;
        this.accountService = accountService;
    }
    run(object, id, cmdOptions) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            if (id != null) {
                id = id.toLowerCase();
            }
            const normalizedOptions = new bw_get_command_Options(cmdOptions);
            switch (object.toLowerCase()) {
                case "item":
                    return yield this.getCipher(id);
                case "username":
                    return yield this.getUsername(id);
                case "password":
                    return yield this.getPassword(id);
                case "uri":
                    return yield this.getUri(id);
                case "totp":
                    return yield this.getTotp(id);
                case "notes":
                    return yield this.getNotes(id);
                case "exposed":
                    return yield this.getExposed(id);
                case "attachment":
                    return yield this.getAttachment(id, normalizedOptions);
                case "folder":
                    return yield this.getFolder(id);
                case "collection":
                    return yield this.getCollection(id);
                case "org-collection":
                    return yield this.getOrganizationCollection(id, normalizedOptions);
                case "organization":
                    return yield this.getOrganization(id);
                case "template":
                    return yield this.getTemplate(id);
                case "fingerprint":
                    return yield this.getFingerprint(id);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    getCipherView(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let decCipher = null;
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            if (bw_utils_Utils.isGuid(id)) {
                const cipher = yield this.cipherService.get(id, activeUserId);
                if (cipher != null) {
                    decCipher = yield cipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(cipher, activeUserId));
                }
            }
            else if (id.trim() !== "") {
                let ciphers = yield this.cipherService.getAllDecrypted(activeUserId);
                ciphers = this.searchService.searchCiphersBasic(ciphers, id);
                if (ciphers.length > 1) {
                    return ciphers;
                }
                if (ciphers.length > 0) {
                    decCipher = ciphers[0];
                }
            }
            return decCipher;
        });
    }
    getCipher(id, filter) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let decCipher = yield this.getCipherView(id);
            if (decCipher == null) {
                return bw_Response.notFound();
            }
            if (Array.isArray(decCipher)) {
                if (filter != null) {
                    decCipher = decCipher.filter(filter);
                    if (decCipher.length === 1) {
                        decCipher = decCipher[0];
                    }
                }
                if (Array.isArray(decCipher)) {
                    return bw_Response.multipleResults(decCipher.map((c) => c.id));
                }
            }
            yield this.eventCollectionService.collect(bw_EventType.Cipher_ClientViewed, decCipher.id, true, decCipher.organizationId);
            const res = new bw_CipherResponse(decCipher);
            return bw_Response.success(res);
        });
    }
    getUsername(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            const cipherResponse = yield this.getCipher(id, (c) => c.type === bw_CipherType.Login && !bw_utils_Utils.isNullOrWhitespace(c.login.username));
            if (!cipherResponse.success) {
                return cipherResponse;
            }
            const cipher = cipherResponse.data;
            if (cipher.type !== bw_CipherType.Login) {
                return bw_Response.badRequest("Not a login.");
            }
            if (bw_utils_Utils.isNullOrWhitespace(cipher.login.username)) {
                return bw_Response.error("No username available for this login.");
            }
            const res = new bw_StringResponse(cipher.login.username);
            return bw_Response.success(res);
        });
    }
    getPassword(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            const cipherResponse = yield this.getCipher(id, (c) => c.type === bw_CipherType.Login && !bw_utils_Utils.isNullOrWhitespace(c.login.password));
            if (!cipherResponse.success) {
                return cipherResponse;
            }
            const cipher = cipherResponse.data;
            if (cipher.type !== bw_CipherType.Login) {
                return bw_Response.badRequest("Not a login.");
            }
            if (bw_utils_Utils.isNullOrWhitespace(cipher.login.password)) {
                return bw_Response.error("No password available for this login.");
            }
            const res = new bw_StringResponse(cipher.login.password);
            return bw_Response.success(res);
        });
    }
    getUri(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            const cipherResponse = yield this.getCipher(id, (c) => c.type === bw_CipherType.Login &&
                c.login.uris != null &&
                c.login.uris.length > 0 &&
                c.login.uris[0].uri !== "");
            if (!cipherResponse.success) {
                return cipherResponse;
            }
            const cipher = cipherResponse.data;
            if (cipher.type !== bw_CipherType.Login) {
                return bw_Response.badRequest("Not a login.");
            }
            if (cipher.login.uris == null ||
                cipher.login.uris.length === 0 ||
                cipher.login.uris[0].uri === "") {
                return bw_Response.error("No uri available for this login.");
            }
            const res = new bw_StringResponse(cipher.login.uris[0].uri);
            return bw_Response.success(res);
        });
    }
    getTotp(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            const cipherResponse = yield this.getCipher(id, (c) => c.type === bw_CipherType.Login && !bw_utils_Utils.isNullOrWhitespace(c.login.totp));
            if (!cipherResponse.success) {
                return cipherResponse;
            }
            const cipher = cipherResponse.data;
            if (cipher.type !== bw_CipherType.Login) {
                return bw_Response.badRequest("Not a login.");
            }
            if (bw_utils_Utils.isNullOrWhitespace(cipher.login.totp)) {
                return bw_Response.error("No TOTP available for this login.");
            }
            const totpResponse = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.totpService.getCode$(cipher.login.totp));
            if (!totpResponse.code) {
                return bw_Response.error("Couldn't generate TOTP code.");
            }
            const account = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            const canAccessPremium = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountProfileService.hasPremiumFromAnySource$(account.id));
            if (!canAccessPremium) {
                const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
                const originalCipher = yield this.cipherService.get(cipher.id, activeUserId);
                if (originalCipher == null ||
                    originalCipher.organizationId == null ||
                    !originalCipher.organizationUseTotp) {
                    return bw_Response.error("Premium status is required to use this feature.");
                }
            }
            const res = new bw_StringResponse(totpResponse.code);
            return bw_Response.success(res);
        });
    }
    getNotes(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            const cipherResponse = yield this.getCipher(id, (c) => !bw_utils_Utils.isNullOrWhitespace(c.notes));
            if (!cipherResponse.success) {
                return cipherResponse;
            }
            const cipher = cipherResponse.data;
            if (bw_utils_Utils.isNullOrWhitespace(cipher.notes)) {
                return bw_Response.error("No notes available for this item.");
            }
            const res = new bw_StringResponse(cipher.notes);
            return bw_Response.success(res);
        });
    }
    getExposed(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            const passwordResponse = yield this.getPassword(id);
            if (!passwordResponse.success) {
                return passwordResponse;
            }
            const exposedNumber = yield this.auditService.passwordLeaked(passwordResponse.data.data);
            const res = new bw_StringResponse(exposedNumber.toString());
            return bw_Response.success(res);
        });
    }
    getAttachment(id, options) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            if (options.itemId == null || options.itemId === "") {
                return bw_Response.badRequest("--itemid <itemid> required.");
            }
            const itemId = options.itemId.toLowerCase();
            const cipherResponse = yield this.getCipher(itemId);
            if (!cipherResponse.success) {
                return cipherResponse;
            }
            const cipher = yield this.getCipherView(itemId);
            if (cipher == null ||
                Array.isArray(cipher) ||
                cipher.attachments == null ||
                cipher.attachments.length === 0) {
                return bw_Response.error("No attachments available for this item.");
            }
            let attachments = cipher.attachments.filter((a) => a.id.toLowerCase() === id ||
                (a.fileName != null && a.fileName.toLowerCase().indexOf(id) > -1));
            if (attachments.length === 0) {
                return bw_Response.error("Attachment `" + id + "` was not found.");
            }
            const exactMatches = attachments.filter((a) => a.fileName.toLowerCase() === id);
            if (exactMatches.length === 1) {
                attachments = exactMatches;
            }
            if (attachments.length > 1) {
                return bw_Response.multipleResults(attachments.map((a) => a.id));
            }
            const account = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            const canAccessPremium = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountProfileService.hasPremiumFromAnySource$(account.id));
            if (!canAccessPremium) {
                const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
                const originalCipher = yield this.cipherService.get(cipher.id, activeUserId);
                if (originalCipher == null || originalCipher.organizationId == null) {
                    return bw_Response.error("Premium status is required to use this feature.");
                }
            }
            let url;
            try {
                const attachmentDownloadResponse = yield this.apiService.getAttachmentData(cipher.id, attachments[0].id);
                url = attachmentDownloadResponse.url;
            }
            catch (e) {
                if (e instanceof bw_ErrorResponse && e.statusCode === 404) {
                    url = attachments[0].url;
                }
                else if (e instanceof bw_ErrorResponse) {
                    throw new Error(e.getSingleMessage());
                }
                else {
                    throw e;
                }
            }
            const key = attachments[0].key != null
                ? attachments[0].key
                : yield this.keyService.getOrgKey(cipher.organizationId);
            return yield this.saveAttachmentToFile(url, key, attachments[0].fileName, options.output);
        });
    }
    getFolder(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let decFolder = null;
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            if (bw_utils_Utils.isGuid(id)) {
                const folder = yield this.folderService.getFromState(id, activeUserId);
                if (folder != null) {
                    decFolder = yield folder.decrypt();
                }
            }
            else if (id.trim() !== "") {
                let folders = yield this.folderService.getAllDecryptedFromState(activeUserId);
                folders = bw_CliUtils.searchFolders(folders, id);
                if (folders.length > 1) {
                    return bw_Response.multipleResults(folders.map((f) => f.id));
                }
                if (folders.length > 0) {
                    decFolder = folders[0];
                }
            }
            if (decFolder == null) {
                return bw_Response.notFound();
            }
            const res = new bw_FolderResponse(decFolder);
            return bw_Response.success(res);
        });
    }
    getCollection(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let decCollection = null;
            if (bw_utils_Utils.isGuid(id)) {
                const collection = yield this.collectionService.get(id);
                if (collection != null) {
                    const orgKeys = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.activeUserOrgKeys$);
                    decCollection = yield collection.decrypt(orgKeys[collection.organizationId]);
                }
            }
            else if (id.trim() !== "") {
                let collections = yield this.collectionService.getAllDecrypted();
                collections = bw_CliUtils.searchCollections(collections, id);
                if (collections.length > 1) {
                    return bw_Response.multipleResults(collections.map((c) => c.id));
                }
                if (collections.length > 0) {
                    decCollection = collections[0];
                }
            }
            if (decCollection == null) {
                return bw_Response.notFound();
            }
            const res = new bw_collection_response_CollectionResponse(decCollection);
            return bw_Response.success(res);
        });
    }
    getOrganizationCollection(id, options) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("`organizationid` option is required.");
            }
            if (!bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            try {
                const orgKey = yield this.keyService.getOrgKey(options.organizationId);
                if (orgKey == null) {
                    throw new Error("No encryption key for this organization.");
                }
                const response = yield this.apiService.getCollectionAccessDetails(options.organizationId, id);
                const decCollection = new bw_CollectionView(response);
                decCollection.name = yield this.encryptService.decryptToUtf8(new bw_enc_string_EncString(response.name), orgKey, `orgkey-${options.organizationId}`);
                const groups = response.groups == null
                    ? null
                    : response.groups.map((g) => new bw_SelectionReadOnly(g.id, g.readOnly, g.hidePasswords, g.manage));
                const users = response.users == null
                    ? null
                    : response.users.map((g) => new bw_SelectionReadOnly(g.id, g.readOnly, g.hidePasswords, g.manage));
                const res = new bw_OrganizationCollectionResponse(decCollection, groups, users);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    getOrganization(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let org = null;
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            if (bw_utils_Utils.isGuid(id)) {
                org = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                    .organizations$(userId)
                    .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations.find((o) => o.id === id))));
            }
            else if (id.trim() !== "") {
                let orgs = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService.organizations$(userId));
                orgs = bw_CliUtils.searchOrganizations(orgs, id);
                if (orgs.length > 1) {
                    return bw_Response.multipleResults(orgs.map((c) => c.id));
                }
                if (orgs.length > 0) {
                    org = orgs[0];
                }
            }
            if (org == null) {
                return bw_Response.notFound();
            }
            const res = new bw_OrganizationResponse(org);
            return bw_Response.success(res);
        });
    }
    getTemplate(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let template = null;
            switch (id.toLowerCase()) {
                case "item":
                    template = bw_CipherExport.template();
                    break;
                case "item.field":
                    template = bw_FieldExport.template();
                    break;
                case "item.login":
                    template = bw_LoginExport.template();
                    break;
                case "item.login.uri":
                    template = bw_LoginUriExport.template();
                    break;
                case "item.card":
                    template = bw_CardExport.template();
                    break;
                case "item.identity":
                    template = bw_IdentityExport.template();
                    break;
                case "item.securenote":
                    template = bw_SecureNoteExport.template();
                    break;
                case "folder":
                    template = bw_FolderExport.template();
                    break;
                case "collection":
                    template = bw_CollectionExport.template();
                    break;
                case "item-collections":
                    template = ["collection-id1", "collection-id2"];
                    break;
                case "org-collection":
                    template = bw_OrganizationCollectionRequest.template();
                    break;
                case "send.text":
                    template = bw_SendResponse.template(bw_SendType.Text);
                    break;
                case "send.file":
                    template = bw_SendResponse.template(bw_SendType.File);
                    break;
                default:
                    return bw_Response.badRequest("Unknown template object.");
            }
            const res = new bw_TemplateResponse(template);
            return bw_Response.success(res);
        });
    }
    getFingerprint(id) {
        return bw_get_command_awaiter(this, void 0, void 0, function* () {
            let fingerprint = null;
            if (id === "me") {
                const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
                const publicKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.userPublicKey$(activeUserId));
                fingerprint = yield this.keyService.getFingerprint(activeUserId, publicKey);
            }
            else if (bw_utils_Utils.isGuid(id)) {
                try {
                    const response = yield this.apiService.getUserPublicKey(id);
                    const pubKey = bw_utils_Utils.fromB64ToArray(response.publicKey);
                    fingerprint = yield this.keyService.getFingerprint(id, pubKey);
                }
                catch (_a) {
                    // empty - handled by the null check below
                }
            }
            if (fingerprint == null) {
                return bw_Response.notFound();
            }
            const res = new bw_StringResponse(fingerprint.join("-"));
            return bw_Response.success(res);
        });
    }
}
class bw_get_command_Options {
    constructor(passedOptions) {
        this.organizationId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationId);
        this.itemId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemId);
        this.output = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.output;
    }
}

;// ./src/tools/send/commands/create.command.ts
var bw_create_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore









class bw_SendCreateCommand {
    constructor(sendService, environmentService, sendApiService, accountProfileService, accountService) {
        this.sendService = sendService;
        this.environmentService = environmentService;
        this.sendApiService = sendApiService;
        this.accountProfileService = accountProfileService;
        this.accountService = accountService;
    }
    run(requestJson, cmdOptions) {
        return bw_create_command_awaiter(this, void 0, void 0, function* () {
            let req = null;
            if (process.env.BW_SERVE !== "true" && (requestJson == null || requestJson === "")) {
                requestJson = yield bw_CliUtils.readStdin();
            }
            if (requestJson == null || requestJson === "") {
                return bw_Response.badRequest("`requestJson` was not provided.");
            }
            if (typeof requestJson !== "string") {
                req = requestJson;
                req.deletionDate = req.deletionDate == null ? null : new Date(req.deletionDate);
                req.expirationDate = req.expirationDate == null ? null : new Date(req.expirationDate);
            }
            else {
                try {
                    const reqJson = Buffer.from(requestJson, "base64").toString();
                    req = bw_SendResponse.fromJson(reqJson);
                    if (req == null) {
                        throw new Error("Null request");
                    }
                    // FIXME: Remove when updating file. Eslint update
                    // eslint-disable-next-line @typescript-eslint/no-unused-vars
                }
                catch (e) {
                    return bw_Response.badRequest("Error parsing the encoded request data.");
                }
            }
            if (req.deletionDate == null ||
                isNaN(new Date(req.deletionDate).getTime()) ||
                new Date(req.deletionDate) <= new Date()) {
                return bw_Response.badRequest("Must specify a valid deletion date after the current time");
            }
            if (req.expirationDate != null && isNaN(new Date(req.expirationDate).getTime())) {
                return bw_Response.badRequest("Unable to parse expirationDate: " + req.expirationDate);
            }
            const normalizedOptions = new bw_create_command_Options(cmdOptions);
            return this.createSend(req, normalizedOptions);
        });
    }
    createSend(req, options) {
        return bw_create_command_awaiter(this, void 0, void 0, function* () {
            var _a, _b, _c, _d, _e, _f, _g, _h;
            const filePath = (_b = (_a = req.file) === null || _a === void 0 ? void 0 : _a.fileName) !== null && _b !== void 0 ? _b : options.file;
            const text = (_d = (_c = req.text) === null || _c === void 0 ? void 0 : _c.text) !== null && _d !== void 0 ? _d : options.text;
            const hidden = (_f = (_e = req.text) === null || _e === void 0 ? void 0 : _e.hidden) !== null && _f !== void 0 ? _f : options.hidden;
            const password = (_g = req.password) !== null && _g !== void 0 ? _g : options.password;
            const maxAccessCount = (_h = req.maxAccessCount) !== null && _h !== void 0 ? _h : options.maxAccessCount;
            req.key = null;
            req.maxAccessCount = maxAccessCount;
            const hasPremium$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)(({ id }) => this.accountProfileService.hasPremiumFromAnySource$(id)));
            switch (req.type) {
                case bw_SendType.File:
                    if (process.env.BW_SERVE === "true") {
                        return bw_Response.error("Creating a file-based Send is unsupported through the `serve` command at this time.");
                    }
                    if (!(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(hasPremium$))) {
                        return bw_Response.error("Premium status is required to use this feature.");
                    }
                    if (filePath == null) {
                        return bw_Response.badRequest("Must specify a file to Send either with the --file option or in the request JSON.");
                    }
                    req.file.fileName = bw_external_path_namespaceObject.basename(filePath);
                    break;
                case bw_SendType.Text:
                    if (text == null) {
                        return bw_Response.badRequest("Must specify text content to Send either with the --text option or in the request JSON.");
                    }
                    req.text = new bw_SendTextResponse();
                    req.text.text = text;
                    req.text.hidden = hidden;
                    break;
                default:
                    return bw_Response.badRequest("Unknown Send type " + bw_SendType[req.type] + ". Valid types are: file, text");
            }
            try {
                let fileBuffer = null;
                if (req.type === bw_SendType.File) {
                    fileBuffer = bw_NodeUtils.bufferToArrayBuffer(bw_external_fs_namespaceObject.readFileSync(filePath));
                }
                const sendView = bw_SendResponse.toView(req);
                const [encSend, fileData] = yield this.sendService.encrypt(sendView, fileBuffer, password);
                // Add dates from template
                encSend.deletionDate = sendView.deletionDate;
                encSend.expirationDate = sendView.expirationDate;
                yield this.sendApiService.save([encSend, fileData]);
                const newSend = yield this.sendService.getFromState(encSend.id);
                const decSend = yield newSend.decrypt();
                const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
                const res = new bw_SendResponse(decSend, env.getWebVaultUrl());
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}
class bw_create_command_Options {
    constructor(passedOptions) {
        this.file = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.file;
        this.text = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.text;
        this.password = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.password;
        this.hidden = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.hidden);
        this.maxAccessCount =
            (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.maxAccessCount) != null ? parseInt(passedOptions.maxAccessCount, null) : null;
    }
}

;// ./src/tools/send/commands/delete.command.ts
var bw_delete_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_SendDeleteCommand {
    constructor(sendService, sendApiService) {
        this.sendService = sendService;
        this.sendApiService = sendApiService;
    }
    run(id) {
        return bw_delete_command_awaiter(this, void 0, void 0, function* () {
            const send = yield this.sendService.getFromState(id);
            if (send == null) {
                return bw_Response.notFound();
            }
            try {
                yield this.sendApiService.delete(id);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}

;// ./src/tools/send/commands/edit.command.ts
var bw_edit_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_SendEditCommand {
    constructor(sendService, getCommand, sendApiService, accountProfileService, accountService) {
        this.sendService = sendService;
        this.getCommand = getCommand;
        this.sendApiService = sendApiService;
        this.accountProfileService = accountProfileService;
        this.accountService = accountService;
    }
    run(requestJson, cmdOptions) {
        return bw_edit_command_awaiter(this, void 0, void 0, function* () {
            if (process.env.BW_SERVE !== "true" && (requestJson == null || requestJson === "")) {
                requestJson = yield bw_CliUtils.readStdin();
            }
            if (requestJson == null || requestJson === "") {
                return bw_Response.badRequest("`requestJson` was not provided.");
            }
            let req = null;
            if (typeof requestJson !== "string") {
                req = requestJson;
                req.deletionDate = req.deletionDate == null ? null : new Date(req.deletionDate);
                req.expirationDate = req.expirationDate == null ? null : new Date(req.expirationDate);
            }
            else {
                try {
                    const reqJson = Buffer.from(requestJson, "base64").toString();
                    req = bw_SendResponse.fromJson(reqJson);
                    // FIXME: Remove when updating file. Eslint update
                    // eslint-disable-next-line @typescript-eslint/no-unused-vars
                }
                catch (e) {
                    return bw_Response.badRequest("Error parsing the encoded request data.");
                }
            }
            const normalizedOptions = new bw_edit_command_Options(cmdOptions);
            req.id = normalizedOptions.itemId || req.id;
            if (req.id != null) {
                req.id = req.id.toLowerCase();
            }
            const send = yield this.sendService.getFromState(req.id);
            if (send == null) {
                return bw_Response.notFound();
            }
            if (send.type !== req.type) {
                return bw_Response.badRequest("Cannot change a Send's type");
            }
            const account = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            const canAccessPremium = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountProfileService.hasPremiumFromAnySource$(account.id));
            if (send.type === bw_SendType.File && !canAccessPremium) {
                return bw_Response.error("Premium status is required to use this feature.");
            }
            let sendView = yield send.decrypt();
            sendView = bw_SendResponse.toView(req, sendView);
            if (typeof req.password !== "string" || req.password === "") {
                req.password = null;
            }
            try {
                const [encSend, encFileData] = yield this.sendService.encrypt(sendView, null, req.password);
                // Add dates from template
                encSend.deletionDate = sendView.deletionDate;
                encSend.expirationDate = sendView.expirationDate;
                yield this.sendApiService.save([encSend, encFileData]);
            }
            catch (e) {
                return bw_Response.error(e);
            }
            return yield this.getCommand.run(send.id, {});
        });
    }
}
class bw_edit_command_Options {
    constructor(passedOptions) {
        this.itemId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemId) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemid);
    }
}

;// ./src/tools/send/commands/get.command.ts
var bw_commands_get_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_SendGetCommand extends bw_DownloadCommand {
    constructor(sendService, environmentService, searchService, encryptService, apiService) {
        super(encryptService, apiService);
        this.sendService = sendService;
        this.environmentService = environmentService;
        this.searchService = searchService;
    }
    run(id, options) {
        return bw_commands_get_command_awaiter(this, void 0, void 0, function* () {
            const serveCommand = process.env.BW_SERVE === "true";
            if (serveCommand && !bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            let sends = yield this.getSendView(id);
            if (sends == null) {
                return bw_Response.notFound();
            }
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const webVaultUrl = env.getWebVaultUrl();
            let filter = (s) => true;
            let selector = (s) => bw_commands_get_command_awaiter(this, void 0, void 0, function* () { return bw_Response.success(new bw_SendResponse(s, webVaultUrl)); });
            if (!serveCommand && (options === null || options === void 0 ? void 0 : options.text) != null) {
                filter = (s) => {
                    return filter(s) && s.text != null;
                };
                selector = (s) => bw_commands_get_command_awaiter(this, void 0, void 0, function* () {
                    // Write to stdout and response success so we get the text string only to stdout
                    process.stdout.write(s.text.text);
                    return bw_Response.success();
                });
            }
            if (Array.isArray(sends)) {
                if (filter != null) {
                    sends = sends.filter(filter);
                }
                if (sends.length > 1) {
                    return bw_Response.multipleResults(sends.map((s) => s.id));
                }
                if (sends.length > 0) {
                    return selector(sends[0]);
                }
                else {
                    return bw_Response.notFound();
                }
            }
            return selector(sends);
        });
    }
    getSendView(id) {
        return bw_commands_get_command_awaiter(this, void 0, void 0, function* () {
            if (bw_utils_Utils.isGuid(id)) {
                const send = yield this.sendService.getFromState(id);
                if (send != null) {
                    return yield send.decrypt();
                }
            }
            else if (id.trim() !== "") {
                let sends = yield this.sendService.getAllDecryptedFromState();
                sends = this.searchService.searchSends(sends, id);
                if (sends.length > 1) {
                    return sends;
                }
                else if (sends.length > 0) {
                    return sends[0];
                }
            }
        });
    }
}

;// ./src/models/response/list.response.ts
class bw_list_response_ListResponse {
    constructor(data) {
        this.object = "list";
        this.data = data;
    }
}

;// ./src/tools/send/commands/list.command.ts
var bw_list_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_SendListCommand {
    constructor(sendService, environmentService, searchService) {
        this.sendService = sendService;
        this.environmentService = environmentService;
        this.searchService = searchService;
    }
    run(cmdOptions) {
        return bw_list_command_awaiter(this, void 0, void 0, function* () {
            let sends = yield this.sendService.getAllDecryptedFromState();
            const normalizedOptions = new bw_list_command_Options(cmdOptions);
            if (normalizedOptions.search != null && normalizedOptions.search.trim() !== "") {
                sends = this.searchService.searchSends(sends, normalizedOptions.search);
            }
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const webVaultUrl = env.getWebVaultUrl();
            const res = new bw_list_response_ListResponse(sends.map((s) => new bw_SendResponse(s, webVaultUrl)));
            return bw_Response.success(res);
        });
    }
}
class bw_list_command_Options {
    constructor(passedOptions) {
        this.search = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.search;
    }
}

;// ../../libs/common/src/tools/send/models/view/send-access.view.ts


class bw_SendAccessView {
    constructor(s) {
        this.id = null;
        this.name = null;
        this.type = null;
        this.text = new bw_SendTextView();
        this.file = new bw_SendFileView();
        this.expirationDate = null;
        this.creatorIdentifier = null;
        if (!s) {
            return;
        }
        this.id = s.id;
        this.type = s.type;
        this.expirationDate = s.expirationDate;
        this.creatorIdentifier = s.creatorIdentifier;
    }
}

;// ../../libs/common/src/tools/send/models/domain/send-file.ts
var bw_send_file_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_SendFile extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.size = obj.size;
        this.buildDomainModel(this, obj, {
            id: null,
            sizeName: null,
            fileName: null,
        }, ["id", "sizeName"]);
    }
    decrypt(key) {
        return bw_send_file_awaiter(this, void 0, void 0, function* () {
            return yield this.decryptObj(this, new bw_SendFileView(this), ["fileName"], null, key);
        });
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return Object.assign(new bw_SendFile(), obj, {
            fileName: bw_enc_string_EncString.fromJSON(obj.fileName),
        });
    }
}

;// ../../libs/common/src/tools/send/models/domain/send-text.ts



class bw_SendText extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.hidden = obj.hidden;
        this.buildDomainModel(this, obj, {
            text: null,
        }, []);
    }
    decrypt(key) {
        return this.decryptObj(this, new bw_SendTextView(this), ["text"], null, key);
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return Object.assign(new bw_SendText(), obj, {
            text: bw_enc_string_EncString.fromJSON(obj.text),
        });
    }
}

;// ../../libs/common/src/tools/send/models/domain/send-access.ts
var bw_send_access_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_SendAccess extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            id: null,
            name: null,
            expirationDate: null,
            creatorIdentifier: null,
        }, ["id", "expirationDate", "creatorIdentifier"]);
        this.type = obj.type;
        switch (this.type) {
            case bw_SendType.Text:
                this.text = new bw_SendText(obj.text);
                break;
            case bw_SendType.File:
                this.file = new bw_SendFile(obj.file);
                break;
            default:
                break;
        }
    }
    decrypt(key) {
        return bw_send_access_awaiter(this, void 0, void 0, function* () {
            const model = new bw_SendAccessView(this);
            yield this.decryptObj(this, model, ["name"], null, key);
            switch (this.type) {
                case bw_SendType.File:
                    model.file = yield this.file.decrypt(key);
                    break;
                case bw_SendType.Text:
                    model.text = yield this.text.decrypt(key);
                    break;
                default:
                    break;
            }
            return model;
        });
    }
}

;// ../../libs/common/src/tools/send/models/request/send-access.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_SendAccessRequest {
}

;// ./src/tools/send/models/send-access.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_SendAccessResponse {
    static template() {
        const req = new bw_SendAccessResponse();
        req.name = "Send name";
        req.type = bw_SendType.Text;
        req.text = null;
        req.file = null;
        return req;
    }
    constructor(o) {
        this.object = "send-access";
        if (o == null) {
            return;
        }
        this.id = o.id;
        this.name = o.name;
        this.type = o.type;
        if (o.type === bw_SendType.Text && o.text != null) {
            this.text = new bw_SendTextResponse(o.text);
        }
        if (o.type === bw_SendType.File && o.file != null) {
            this.file = new bw_SendFileResponse(o.file);
        }
    }
}

;// ./src/tools/send/commands/receive.command.ts
var bw_receive_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};











class bw_SendReceiveCommand extends bw_DownloadCommand {
    constructor(keyService, encryptService, cryptoFunctionService, platformUtilsService, environmentService, sendApiService, apiService) {
        super(encryptService, apiService);
        this.keyService = keyService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.platformUtilsService = platformUtilsService;
        this.environmentService = environmentService;
        this.sendApiService = sendApiService;
    }
    run(url, options) {
        return bw_receive_command_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            this.canInteract = process.env.BW_NOINTERACTION !== "true";
            let urlObject;
            try {
                urlObject = new URL(url);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                return bw_Response.badRequest("Failed to parse the provided Send url");
            }
            const apiUrl = yield this.getApiUrl(urlObject);
            const [id, key] = this.getIdAndKey(urlObject);
            if (bw_utils_Utils.isNullOrWhitespace(id) || bw_utils_Utils.isNullOrWhitespace(key)) {
                return bw_Response.badRequest("Failed to parse url, the url provided is not a valid Send url");
            }
            const keyArray = bw_utils_Utils.fromUrlB64ToArray(key);
            this.sendAccessRequest = new bw_SendAccessRequest();
            let password = options.password;
            if (password == null || password === "") {
                if (options.passwordfile) {
                    password = yield bw_NodeUtils.readFirstLine(options.passwordfile);
                }
                else if (options.passwordenv && process.env[options.passwordenv]) {
                    password = process.env[options.passwordenv];
                }
            }
            if (password != null && password !== "") {
                this.sendAccessRequest.password = yield this.getUnlockedPassword(password, keyArray);
            }
            const response = yield this.sendRequest(apiUrl, id, keyArray);
            if (response instanceof bw_Response) {
                // Error scenario
                return response;
            }
            if (options.obj != null) {
                return bw_Response.success(new bw_SendAccessResponse(response));
            }
            switch (response.type) {
                case bw_SendType.Text:
                    // Write to stdout and response success so we get the text string only to stdout
                    process.stdout.write((_a = response === null || response === void 0 ? void 0 : response.text) === null || _a === void 0 ? void 0 : _a.text);
                    return bw_Response.success();
                case bw_SendType.File: {
                    const downloadData = yield this.sendApiService.getSendFileDownloadData(response, this.sendAccessRequest, apiUrl);
                    return yield this.saveAttachmentToFile(downloadData.url, this.decKey, (_b = response === null || response === void 0 ? void 0 : response.file) === null || _b === void 0 ? void 0 : _b.fileName, options.output);
                }
                default:
                    return bw_Response.success(new bw_SendAccessResponse(response));
            }
        });
    }
    getIdAndKey(url) {
        const result = url.hash.slice(1).split("/").slice(-2);
        return [result[0], result[1]];
    }
    getApiUrl(url) {
        return bw_receive_command_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const urls = env.getUrls();
            if (url.origin === "https://send.bitwarden.com") {
                return "https://api.bitwarden.com";
            }
            else if (url.origin === urls.api) {
                return url.origin;
            }
            else if (this.platformUtilsService.isDev() && url.origin === urls.webVault) {
                return urls.api;
            }
            else {
                return url.origin + "/api";
            }
        });
    }
    getUnlockedPassword(password, keyArray) {
        return bw_receive_command_awaiter(this, void 0, void 0, function* () {
            const passwordHash = yield this.cryptoFunctionService.pbkdf2(password, keyArray, "sha256", 100000);
            return bw_utils_Utils.fromBufferToB64(passwordHash);
        });
    }
    sendRequest(url, id, key) {
        return bw_receive_command_awaiter(this, void 0, void 0, function* () {
            try {
                const sendResponse = yield this.sendApiService.postSendAccess(id, this.sendAccessRequest, url);
                const sendAccess = new bw_SendAccess(sendResponse);
                this.decKey = yield this.keyService.makeSendKey(key);
                return yield sendAccess.decrypt(this.decKey);
            }
            catch (e) {
                if (e instanceof bw_ErrorResponse) {
                    if (e.statusCode === 401) {
                        if (this.canInteract) {
                            const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                                output: process.stderr,
                            })({
                                type: "password",
                                name: "password",
                                message: "Send password:",
                            });
                            // reattempt with new password
                            this.sendAccessRequest.password = yield this.getUnlockedPassword(answer.password, key);
                            return yield this.sendRequest(url, id, key);
                        }
                        return bw_Response.badRequest("Incorrect or missing password");
                    }
                    else if (e.statusCode === 405) {
                        return bw_Response.badRequest("Bad Request");
                    }
                    else if (e.statusCode === 404) {
                        return bw_Response.notFound();
                    }
                }
                return bw_Response.error(e);
            }
        });
    }
}

;// ./src/tools/send/commands/remove-password.command.ts
var bw_remove_password_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_SendRemovePasswordCommand {
    constructor(sendService, sendApiService, environmentService) {
        this.sendService = sendService;
        this.sendApiService = sendApiService;
        this.environmentService = environmentService;
    }
    run(id) {
        return bw_remove_password_command_awaiter(this, void 0, void 0, function* () {
            try {
                yield this.sendApiService.removePassword(id);
                const updatedSend = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.sendService.get$(id));
                const decSend = yield updatedSend.decrypt();
                const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
                const webVaultUrl = env.getWebVaultUrl();
                const res = new bw_SendResponse(decSend, webVaultUrl);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}

;// ./src/tools/send/commands/index.ts








;// ./src/tools/send/send.program.ts
var bw_send_program_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore














const bw_send_program_writeLn = bw_CliUtils.writeLn;
class bw_SendProgram extends bw_BaseProgram {
    register() {
        bw_external_commander_namespaceObject.program.addCommand(this.sendCommand());
        // receive is accessible both at `bw receive` and `bw send receive`
        bw_external_commander_namespaceObject.program.addCommand(this.receiveCommand());
    }
    sendCommand() {
        return new bw_external_commander_namespaceObject.Command("send")
            .argument("<data>", "The data to Send. Specify as a filepath with the --file option")
            .description("Work with Bitwarden sends. A Send can be quickly created using this command or subcommands can be used to fine-tune the Send")
            .option("-f, --file", "Specifies that <data> is a filepath")
            .option("-d, --deleteInDays <days>", "The number of days in the future to set deletion date, defaults to 7", "7")
            .option("-a, --maxAccessCount <amount>", "The amount of max possible accesses.")
            .option("--hidden", "Hide <data> in web by default. Valid only if --file is not set.")
            .option("-n, --name <name>", "The name of the Send. Defaults to a guid for text Sends and the filename for files.")
            .option("--notes <notes>", "Notes to add to the Send.")
            .option("--fullObject", "Specifies that the full Send object should be returned rather than just the access url.")
            .addCommand(this.listCommand())
            .addCommand(this.templateCommand())
            .addCommand(this.getCommand())
            .addCommand(this.receiveCommand())
            .addCommand(this.createCommand())
            .addCommand(this.editCommand())
            .addCommand(this.removePasswordCommand())
            .addCommand(this.deleteCommand())
            .action((data, options) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            const encodedJson = this.makeSendJson(data, options);
            let response;
            if (encodedJson instanceof bw_Response) {
                response = encodedJson;
            }
            else {
                response = yield this.runCreate(encodedJson, options);
            }
            this.processResponse(response);
        }));
    }
    receiveCommand() {
        return new bw_external_commander_namespaceObject.Command("receive")
            .arguments("<url>")
            .description("Access a Bitwarden Send from a url")
            .option("--password <password>", "Password needed to access the Send.")
            .option("--passwordenv <passwordenv>", "Environment variable storing the Send's password")
            .option("--passwordfile <passwordfile>", "Path to a file containing the Sends password as its first line")
            .option("--obj", "Return the Send's json object rather than the Send's content")
            .option("--output <location>", "Specify a file path to save a File-type Send to")
            .on("--help", () => {
            bw_send_program_writeLn("");
            bw_send_program_writeLn("If a password is required, the provided password is used or the user is prompted.");
            bw_send_program_writeLn("", true);
        })
            .action((url, options) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            const cmd = new bw_SendReceiveCommand(this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.cryptoFunctionService, this.serviceContainer.platformUtilsService, this.serviceContainer.environmentService, this.serviceContainer.sendApiService, this.serviceContainer.apiService);
            const response = yield cmd.run(url, options);
            this.processResponse(response);
        }));
    }
    listCommand() {
        return new bw_external_commander_namespaceObject.Command("list")
            .description("List all the Sends owned by you")
            .on("--help", () => {
            bw_send_program_writeLn(bw_external_chalk_namespaceObject("This is in the list command"));
        })
            .action((options) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = new bw_SendListCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.searchService);
            const response = yield cmd.run(options);
            this.processResponse(response);
        }));
    }
    templateCommand() {
        return new bw_external_commander_namespaceObject.Command("template")
            .argument("<object>", "Valid objects are: send.text, send.file")
            .description("Get json templates for send objects")
            .action((object) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            const cmd = new bw_GetCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.collectionService, this.serviceContainer.totpService, this.serviceContainer.auditService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.searchService, this.serviceContainer.apiService, this.serviceContainer.organizationService, this.serviceContainer.eventCollectionService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
            const response = yield cmd.run("template", object, null);
            this.processResponse(response);
        }));
    }
    getCommand() {
        return new bw_external_commander_namespaceObject.Command("get")
            .arguments("<id>")
            .description("Get Sends owned by you.")
            .option("--output <output>", "Output directory or filename for attachment.")
            .option("--text", "Specifies to return the text content of a Send")
            .on("--help", () => {
            bw_send_program_writeLn("");
            bw_send_program_writeLn("  Id:");
            bw_send_program_writeLn("");
            bw_send_program_writeLn("    Search term or Send's globally unique `id`.");
            bw_send_program_writeLn("");
            bw_send_program_writeLn("    If raw output is specified and no output filename or directory is given for");
            bw_send_program_writeLn("    an attachment query, the attachment content is written to stdout.");
            bw_send_program_writeLn("");
            bw_send_program_writeLn("  Examples:");
            bw_send_program_writeLn("");
            bw_send_program_writeLn("    bw send get searchText");
            bw_send_program_writeLn("    bw send get id");
            bw_send_program_writeLn("    bw send get searchText --text");
            bw_send_program_writeLn("    bw send get searchText --file");
            bw_send_program_writeLn("    bw send get searchText --file --output ../Photos/photo.jpg");
            bw_send_program_writeLn("    bw send get searchText --file --raw");
            bw_send_program_writeLn("", true);
        })
            .action((id, options) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = new bw_SendGetCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.searchService, this.serviceContainer.encryptService, this.serviceContainer.apiService);
            const response = yield cmd.run(id, options);
            this.processResponse(response);
        }));
    }
    createCommand() {
        return new bw_external_commander_namespaceObject.Command("create")
            .argument("[encodedJson]", "JSON object to upload. Can also be piped in through stdin.")
            .description("create a Send")
            .option("--file <path>", "file to Send. Can also be specified in parent's JSON.")
            .option("--text <text>", "text to Send. Can also be specified in parent's JSON.")
            .option("--hidden", "text hidden flag. Valid only with the --text option.")
            .option("--password <password>", "optional password to access this Send. Can also be specified in JSON")
            .on("--help", () => {
            bw_send_program_writeLn("");
            bw_send_program_writeLn("Note:");
            bw_send_program_writeLn("  Options specified in JSON take precedence over command options");
            bw_send_program_writeLn("", true);
        })
            .action((encodedJson, options, args) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            // Work-around to support `--fullObject` option for `send create --fullObject`
            // Calling `option('--fullObject', ...)` above won't work due to Commander doesn't like same option
            // to be defind on both parent-command and sub-command
            const { fullObject = false } = args.parent.opts();
            const mergedOptions = Object.assign(Object.assign({}, options), { fullObject: fullObject });
            const response = yield this.runCreate(encodedJson, mergedOptions);
            this.processResponse(response);
        }));
    }
    editCommand() {
        return new bw_external_commander_namespaceObject.Command("edit")
            .argument("[encodedJson]", "Updated JSON object to save. If not provided, encodedJson is read from stdin.")
            .description("edit a Send")
            .option("--itemid <itemid>", "Overrides the itemId provided in [encodedJson]")
            .on("--help", () => {
            bw_send_program_writeLn("");
            bw_send_program_writeLn("Note:");
            bw_send_program_writeLn("  You cannot update a File-type Send's file. Just delete and remake it");
            bw_send_program_writeLn("", true);
        })
            .action((encodedJson, options) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const getCmd = new bw_SendGetCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.searchService, this.serviceContainer.encryptService, this.serviceContainer.apiService);
            const cmd = new bw_SendEditCommand(this.serviceContainer.sendService, getCmd, this.serviceContainer.sendApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
            const response = yield cmd.run(encodedJson, options);
            this.processResponse(response);
        }));
    }
    deleteCommand() {
        return new bw_external_commander_namespaceObject.Command("delete")
            .argument("<id>", "The id of the Send to delete.")
            .description("delete a Send")
            .action((id) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = new bw_SendDeleteCommand(this.serviceContainer.sendService, this.serviceContainer.sendApiService);
            const response = yield cmd.run(id);
            this.processResponse(response);
        }));
    }
    removePasswordCommand() {
        return new bw_external_commander_namespaceObject.Command("remove-password")
            .argument("<id>", "The id of the Send to alter.")
            .description("removes the saved password from a Send.")
            .action((id) => bw_send_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = new bw_SendRemovePasswordCommand(this.serviceContainer.sendService, this.serviceContainer.sendApiService, this.serviceContainer.environmentService);
            const response = yield cmd.run(id);
            this.processResponse(response);
        }));
    }
    makeSendJson(data, options) {
        var _a;
        let sendFile = null;
        let sendText = null;
        let name = bw_utils_Utils.newGuid();
        let type = bw_SendType.Text;
        if (options.file != null) {
            data = bw_external_path_namespaceObject.resolve(data);
            if (!bw_external_fs_namespaceObject.existsSync(data)) {
                return bw_Response.badRequest("data path does not exist");
            }
            sendFile = bw_SendFileResponse.template(data);
            name = bw_external_path_namespaceObject.basename(data);
            type = bw_SendType.File;
        }
        else {
            sendText = bw_SendTextResponse.template(data, options.hidden);
        }
        const template = bw_utils_Utils.assign(bw_SendResponse.template(null, options.deleteInDays), {
            name: (_a = options.name) !== null && _a !== void 0 ? _a : name,
            notes: options.notes,
            file: sendFile,
            text: sendText,
            type: type,
        });
        return Buffer.from(JSON.stringify(template), "utf8").toString("base64");
    }
    runCreate(encodedJson, options) {
        return bw_send_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = new bw_SendCreateCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.sendApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
            return yield cmd.run(encodedJson, options);
        });
    }
}

;// ./src/admin-console/commands/confirm.command.ts
var bw_confirm_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_ConfirmCommand {
    constructor(apiService, keyService, encryptService, organizationUserApiService) {
        this.apiService = apiService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.organizationUserApiService = organizationUserApiService;
    }
    run(object, id, cmdOptions) {
        return bw_confirm_command_awaiter(this, void 0, void 0, function* () {
            if (id != null) {
                id = id.toLowerCase();
            }
            const normalizedOptions = new bw_confirm_command_Options(cmdOptions);
            switch (object.toLowerCase()) {
                case "org-member":
                    return yield this.confirmOrganizationMember(id, normalizedOptions);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    confirmOrganizationMember(id, options) {
        return bw_confirm_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("--organizationid <organizationid> required.");
            }
            if (!bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            try {
                const orgKey = yield this.keyService.getOrgKey(options.organizationId);
                if (orgKey == null) {
                    throw new Error("No encryption key for this organization.");
                }
                const orgUser = yield this.organizationUserApiService.getOrganizationUser(options.organizationId, id);
                if (orgUser == null) {
                    throw new Error("Member id does not exist for this organization.");
                }
                const publicKeyResponse = yield this.apiService.getUserPublicKey(orgUser.userId);
                const publicKey = bw_utils_Utils.fromB64ToArray(publicKeyResponse.publicKey);
                const key = yield this.encryptService.rsaEncrypt(orgKey.key, publicKey);
                const req = new bw_OrganizationUserConfirmRequest();
                req.key = key.encryptedString;
                yield this.organizationUserApiService.postOrganizationUserConfirm(options.organizationId, id, req);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}
class bw_confirm_command_Options {
    constructor(passedOptions) {
        this.organizationId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationId);
    }
}

;// ./src/admin-console/commands/share.command.ts
var bw_share_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_ShareCommand {
    constructor(cipherService, accountService) {
        this.cipherService = cipherService;
        this.accountService = accountService;
    }
    run(id, organizationId, requestJson) {
        return bw_share_command_awaiter(this, void 0, void 0, function* () {
            if (process.env.BW_SERVE !== "true" && (requestJson == null || requestJson === "")) {
                requestJson = yield bw_CliUtils.readStdin();
            }
            if (requestJson == null || requestJson === "") {
                return bw_Response.badRequest("`requestJson` was not provided.");
            }
            let req = [];
            if (typeof requestJson !== "string") {
                req = requestJson;
            }
            else {
                try {
                    const reqJson = Buffer.from(requestJson, "base64").toString();
                    req = JSON.parse(reqJson);
                    if (req == null || req.length === 0) {
                        return bw_Response.badRequest("You must provide at least one collection id for this item.");
                    }
                    // FIXME: Remove when updating file. Eslint update
                    // eslint-disable-next-line @typescript-eslint/no-unused-vars
                }
                catch (e) {
                    return bw_Response.badRequest("Error parsing the encoded request data.");
                }
            }
            if (id != null) {
                id = id.toLowerCase();
            }
            if (organizationId != null) {
                organizationId = organizationId.toLowerCase();
            }
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const cipher = yield this.cipherService.get(id, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            if (cipher.organizationId != null) {
                return bw_Response.badRequest("This item already belongs to an organization.");
            }
            const cipherView = yield cipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(cipher, activeUserId));
            try {
                yield this.cipherService.shareWithServer(cipherView, organizationId, req, activeUserId);
                const updatedCipher = yield this.cipherService.get(cipher.id, activeUserId);
                const decCipher = yield updatedCipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(updatedCipher, activeUserId));
                const res = new bw_CipherResponse(decCipher);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}

;// ../../libs/common/src/admin-console/models/request/selection-read-only.request.ts
class bw_selection_read_only_request_SelectionReadOnlyRequest {
    constructor(id, readOnly, hidePasswords, manage) {
        this.id = id;
        this.readOnly = readOnly;
        this.hidePasswords = hidePasswords;
        this.manage = manage;
    }
}

;// ./src/commands/edit.command.ts
var bw_commands_edit_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore














class bw_EditCommand {
    constructor(cipherService, folderService, keyService, encryptService, apiService, folderApiService, accountService) {
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.apiService = apiService;
        this.folderApiService = folderApiService;
        this.accountService = accountService;
    }
    run(object, id, requestJson, cmdOptions) {
        return bw_commands_edit_command_awaiter(this, void 0, void 0, function* () {
            if (process.env.BW_SERVE !== "true" && (requestJson == null || requestJson === "")) {
                requestJson = yield bw_CliUtils.readStdin();
            }
            if (requestJson == null || requestJson === "") {
                return bw_Response.badRequest("`requestJson` was not provided.");
            }
            let req = null;
            if (typeof requestJson !== "string") {
                req = requestJson;
            }
            else {
                try {
                    const reqJson = Buffer.from(requestJson, "base64").toString();
                    req = JSON.parse(reqJson);
                    // FIXME: Remove when updating file. Eslint update
                    // eslint-disable-next-line @typescript-eslint/no-unused-vars
                }
                catch (e) {
                    return bw_Response.badRequest("Error parsing the encoded request data.");
                }
            }
            if (id != null) {
                id = id.toLowerCase();
            }
            const normalizedOptions = new bw_commands_edit_command_Options(cmdOptions);
            switch (object.toLowerCase()) {
                case "item":
                    return yield this.editCipher(id, req);
                case "item-collections":
                    return yield this.editCipherCollections(id, req);
                case "folder":
                    return yield this.editFolder(id, req);
                case "org-collection":
                    return yield this.editOrganizationCollection(id, req, normalizedOptions);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    editCipher(id, req) {
        return bw_commands_edit_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const cipher = yield this.cipherService.get(id, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            let cipherView = yield cipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(cipher, activeUserId));
            if (cipherView.isDeleted) {
                return bw_Response.badRequest("You may not edit a deleted item. Use the restore command first.");
            }
            cipherView = bw_CipherExport.toView(req, cipherView);
            const encCipher = yield this.cipherService.encrypt(cipherView, activeUserId);
            try {
                const updatedCipher = yield this.cipherService.updateWithServer(encCipher);
                const decCipher = yield updatedCipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(updatedCipher, activeUserId));
                const res = new bw_CipherResponse(decCipher);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    editCipherCollections(id, req) {
        return bw_commands_edit_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const cipher = yield this.cipherService.get(id, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            if (cipher.organizationId == null) {
                return bw_Response.badRequest("Item does not belong to an organization. Consider moving it first.");
            }
            if (!cipher.viewPassword) {
                return bw_Response.noEditPermission();
            }
            cipher.collectionIds = req;
            try {
                const updatedCipher = yield this.cipherService.saveCollectionsWithServer(cipher, activeUserId);
                const decCipher = yield updatedCipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(updatedCipher, yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId))));
                const res = new bw_CipherResponse(decCipher);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    editFolder(id, req) {
        return bw_commands_edit_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const folder = yield this.folderService.getFromState(id, activeUserId);
            if (folder == null) {
                return bw_Response.notFound();
            }
            let folderView = yield folder.decrypt();
            folderView = bw_FolderExport.toView(req, folderView);
            const userKey = yield this.keyService.getUserKeyWithLegacySupport(activeUserId);
            const encFolder = yield this.folderService.encrypt(folderView, userKey);
            try {
                const folder = yield this.folderApiService.save(encFolder, activeUserId);
                const updatedFolder = new bw_Folder(folder);
                const decFolder = yield updatedFolder.decrypt();
                const res = new bw_FolderResponse(decFolder);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    editOrganizationCollection(id, req, options) {
        return bw_commands_edit_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("`organizationid` option is required.");
            }
            if (!bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            if (options.organizationId !== req.organizationId) {
                return bw_Response.badRequest("`organizationid` option does not match request object.");
            }
            try {
                const orgKey = yield this.keyService.getOrgKey(req.organizationId);
                if (orgKey == null) {
                    throw new Error("No encryption key for this organization.");
                }
                const groups = req.groups == null
                    ? null
                    : req.groups.map((g) => new bw_selection_read_only_request_SelectionReadOnlyRequest(g.id, g.readOnly, g.hidePasswords, g.manage));
                const users = req.users == null
                    ? null
                    : req.users.map((u) => new bw_selection_read_only_request_SelectionReadOnlyRequest(u.id, u.readOnly, u.hidePasswords, u.manage));
                const request = new bw_collection_request_CollectionRequest();
                request.name = (yield this.encryptService.encrypt(req.name, orgKey)).encryptedString;
                request.externalId = req.externalId;
                request.groups = groups;
                request.users = users;
                const response = yield this.apiService.putCollection(req.organizationId, id, request);
                const view = bw_CollectionExport.toView(req);
                view.id = response.id;
                const res = new bw_OrganizationCollectionResponse(view, groups, users);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}
class bw_commands_edit_command_Options {
    constructor(passedOptions) {
        this.organizationId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationId);
    }
}

;// ./src/admin-console/models/response/organization-user.response.ts
class bw_organization_user_response_OrganizationUserResponse {
    constructor() {
        this.object = "org-member";
    }
}

;// ./src/commands/list.command.ts
var bw_commands_list_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};













class bw_ListCommand {
    constructor(cipherService, folderService, collectionService, organizationService, searchService, organizationUserApiService, apiService, eventCollectionService, accountService) {
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.collectionService = collectionService;
        this.organizationService = organizationService;
        this.searchService = searchService;
        this.organizationUserApiService = organizationUserApiService;
        this.apiService = apiService;
        this.eventCollectionService = eventCollectionService;
        this.accountService = accountService;
    }
    run(object, cmdOptions) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            const normalizedOptions = new bw_commands_list_command_Options(cmdOptions);
            switch (object.toLowerCase()) {
                case "items":
                    return yield this.listCiphers(normalizedOptions);
                case "folders":
                    return yield this.listFolders(normalizedOptions);
                case "collections":
                    return yield this.listCollections(normalizedOptions);
                case "org-collections":
                    return yield this.listOrganizationCollections(normalizedOptions);
                case "org-members":
                    return yield this.listOrganizationMembers(normalizedOptions);
                case "organizations":
                    return yield this.listOrganizations(normalizedOptions);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    listCiphers(options) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            let ciphers;
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            options.trash = options.trash || false;
            if (options.url != null && options.url.trim() !== "") {
                ciphers = yield this.cipherService.getAllDecryptedForUrl(options.url, activeUserId);
            }
            else {
                ciphers = yield this.cipherService.getAllDecrypted(activeUserId);
            }
            if (options.folderId != null ||
                options.collectionId != null ||
                options.organizationId != null) {
                ciphers = ciphers.filter((c) => {
                    if (options.trash !== c.isDeleted) {
                        return false;
                    }
                    if (options.folderId != null) {
                        if (options.folderId === "notnull" && c.folderId != null) {
                            return true;
                        }
                        const folderId = options.folderId === "null" ? null : options.folderId;
                        if (folderId === c.folderId) {
                            return true;
                        }
                    }
                    if (options.organizationId != null) {
                        if (options.organizationId === "notnull" && c.organizationId != null) {
                            return true;
                        }
                        const organizationId = options.organizationId === "null" ? null : options.organizationId;
                        if (organizationId === c.organizationId) {
                            return true;
                        }
                    }
                    if (options.collectionId != null) {
                        if (options.collectionId === "notnull" &&
                            c.collectionIds != null &&
                            c.collectionIds.length > 0) {
                            return true;
                        }
                        const collectionId = options.collectionId === "null" ? null : options.collectionId;
                        if (collectionId == null && (c.collectionIds == null || c.collectionIds.length === 0)) {
                            return true;
                        }
                        if (collectionId != null &&
                            c.collectionIds != null &&
                            c.collectionIds.indexOf(collectionId) > -1) {
                            return true;
                        }
                    }
                    return false;
                });
            }
            else if (options.search == null || options.search.trim() === "") {
                ciphers = ciphers.filter((c) => options.trash === c.isDeleted);
            }
            if (options.search != null && options.search.trim() !== "") {
                ciphers = this.searchService.searchCiphersBasic(ciphers, options.search, options.trash);
            }
            yield this.eventCollectionService.collectMany(bw_EventType.Cipher_ClientViewed, ciphers, true);
            const res = new bw_list_response_ListResponse(ciphers.map((o) => new bw_CipherResponse(o)));
            return bw_Response.success(res);
        });
    }
    listFolders(options) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            let folders = yield this.folderService.getAllDecryptedFromState(activeUserId);
            if (options.search != null && options.search.trim() !== "") {
                folders = bw_CliUtils.searchFolders(folders, options.search);
            }
            const res = new bw_list_response_ListResponse(folders.map((o) => new bw_FolderResponse(o)));
            return bw_Response.success(res);
        });
    }
    listCollections(options) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            let collections = yield this.collectionService.getAllDecrypted();
            if (options.organizationId != null) {
                collections = collections.filter((c) => {
                    if (options.organizationId === c.organizationId) {
                        return true;
                    }
                    return false;
                });
            }
            if (options.search != null && options.search.trim() !== "") {
                collections = bw_CliUtils.searchCollections(collections, options.search);
            }
            const res = new bw_list_response_ListResponse(collections.map((o) => new bw_collection_response_CollectionResponse(o)));
            return bw_Response.success(res);
        });
    }
    listOrganizationCollections(options) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("`organizationid` option is required.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizatons) => organizatons.find((o) => o.id == options.organizationId))));
            if (organization == null) {
                return bw_Response.error("Organization not found.");
            }
            try {
                let response;
                if (organization.canViewAllCollections) {
                    response = yield this.apiService.getCollections(options.organizationId);
                }
                else {
                    response = yield this.apiService.getUserCollections();
                }
                const collections = response.data
                    .filter((c) => c.organizationId === options.organizationId)
                    .map((r) => new bw_Collection(new bw_collection_data_CollectionData(r)));
                let decCollections = yield this.collectionService.decryptMany(collections);
                if (options.search != null && options.search.trim() !== "") {
                    decCollections = bw_CliUtils.searchCollections(decCollections, options.search);
                }
                const res = new bw_list_response_ListResponse(decCollections.map((o) => new bw_collection_response_CollectionResponse(o)));
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    listOrganizationMembers(options) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("`organizationid` option is required.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizatons) => organizatons.find((o) => o.id == options.organizationId))));
            if (organization == null) {
                return bw_Response.error("Organization not found.");
            }
            try {
                const response = yield this.organizationUserApiService.getAllUsers(options.organizationId);
                const res = new bw_list_response_ListResponse(response.data.map((r) => {
                    const u = new bw_organization_user_response_OrganizationUserResponse();
                    u.email = r.email;
                    u.name = r.name;
                    u.id = r.id;
                    u.status = r.status;
                    u.type = r.type;
                    u.twoFactorEnabled = r.twoFactorEnabled;
                    return u;
                }));
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    listOrganizations(options) {
        return bw_commands_list_command_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            let organizations = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService.memberOrganizations$(userId));
            if (options.search != null && options.search.trim() !== "") {
                organizations = bw_CliUtils.searchOrganizations(organizations, options.search);
            }
            const res = new bw_list_response_ListResponse(organizations.map((o) => new bw_OrganizationResponse(o)));
            return bw_Response.success(res);
        });
    }
}
class bw_commands_list_command_Options {
    constructor(passedOptions) {
        this.organizationId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationId);
        this.collectionId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.collectionid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.collectionId);
        this.folderId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.folderid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.folderId);
        this.search = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.search;
        this.url = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.url;
        this.trash = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.trash);
    }
}

;// ./src/commands/restore.command.ts
var bw_restore_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_RestoreCommand {
    constructor(cipherService, accountService) {
        this.cipherService = cipherService;
        this.accountService = accountService;
    }
    run(object, id) {
        return bw_restore_command_awaiter(this, void 0, void 0, function* () {
            if (id != null) {
                id = id.toLowerCase();
            }
            switch (object.toLowerCase()) {
                case "item":
                    return yield this.restoreCipher(id);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    restoreCipher(id) {
        return bw_restore_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const cipher = yield this.cipherService.get(id, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            if (cipher.deletedDate == null) {
                return bw_Response.badRequest("Cipher is not in trash.");
            }
            try {
                yield this.cipherService.restoreWithServer(id, activeUserId);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}

;// ../../libs/tools/export/vault-export/vault-export-core/src/services/vault-export.service.abstraction.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
const bw_EXPORT_FORMATS = ["csv", "json", "encrypted_json"];
class bw_VaultExportServiceAbstraction {
}

;// ../../libs/tools/export/vault-export/vault-export-core/src/services/export-helper.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_ExportHelper {
    static getFileName(prefix = null, extension = "csv") {
        const now = new Date();
        const dateString = now.getFullYear() +
            "" +
            this.padNumber(now.getMonth() + 1, 2) +
            "" +
            this.padNumber(now.getDate(), 2) +
            this.padNumber(now.getHours(), 2) +
            "" +
            this.padNumber(now.getMinutes(), 2) +
            this.padNumber(now.getSeconds(), 2);
        return "bitwarden" + (prefix ? "_" + prefix : "") + "_export_" + dateString + "." + extension;
    }
    static padNumber(num, width, padCharacter = "0") {
        const numString = num.toString();
        return numString.length >= width
            ? numString
            : new Array(width - numString.length + 1).join(padCharacter) + numString;
    }
}

;// ../../libs/tools/export/vault-export/vault-export-core/src/services/vault-export.service.ts
var bw_vault_export_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_VaultExportService {
    constructor(individualVaultExportService, organizationVaultExportService) {
        this.individualVaultExportService = individualVaultExportService;
        this.organizationVaultExportService = organizationVaultExportService;
    }
    getExport() {
        return bw_vault_export_service_awaiter(this, arguments, void 0, function* (format = "csv", password) {
            if (!bw_utils_Utils.isNullOrWhitespace(password)) {
                if (format == "csv") {
                    throw new Error("CSV does not support password protected export");
                }
                return this.individualVaultExportService.getPasswordProtectedExport(password);
            }
            return this.individualVaultExportService.getExport(format);
        });
    }
    getOrganizationExport(organizationId_1, format_1, password_1) {
        return bw_vault_export_service_awaiter(this, arguments, void 0, function* (organizationId, format, password, onlyManagedCollections = false) {
            if (!bw_utils_Utils.isNullOrWhitespace(password)) {
                if (format == "csv") {
                    throw new Error("CSV does not support password protected export");
                }
                return this.organizationVaultExportService.getPasswordProtectedExport(organizationId, password, onlyManagedCollections);
            }
            return this.organizationVaultExportService.getOrganizationExport(organizationId, format, onlyManagedCollections);
        });
    }
    getFileName(prefix = null, extension = "csv") {
        return bw_ExportHelper.getFileName(prefix, extension);
    }
}

;// external "papaparse"
const bw_external_papaparse_namespaceObject = require("papaparse");
;// ../../libs/tools/export/vault-export/vault-export-core/src/services/base-vault-export.service.ts
var bw_base_vault_export_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_BaseVaultExportService {
    constructor(pinService, encryptService, cryptoFunctionService, kdfConfigService) {
        this.pinService = pinService;
        this.encryptService = encryptService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.kdfConfigService = kdfConfigService;
    }
    buildPasswordExport(clearText, password) {
        return bw_base_vault_export_service_awaiter(this, void 0, void 0, function* () {
            const kdfConfig = yield this.kdfConfigService.getKdfConfig();
            const salt = bw_utils_Utils.fromBufferToB64(yield this.cryptoFunctionService.randomBytes(16));
            const key = yield this.pinService.makePinKey(password, salt, kdfConfig);
            const encKeyValidation = yield this.encryptService.encrypt(bw_utils_Utils.newGuid(), key);
            const encText = yield this.encryptService.encrypt(clearText, key);
            const jsonDoc = {
                encrypted: true,
                passwordProtected: true,
                salt: salt,
                kdfType: kdfConfig.kdfType,
                kdfIterations: kdfConfig.iterations,
                encKeyValidation_DO_NOT_EDIT: encKeyValidation.encryptedString,
                data: encText.encryptedString,
            };
            if (kdfConfig.kdfType === bw_KdfType.Argon2id) {
                jsonDoc.kdfMemory = kdfConfig.memory;
                jsonDoc.kdfParallelism = kdfConfig.parallelism;
            }
            return JSON.stringify(jsonDoc, null, "  ");
        });
    }
    buildCommonCipher(cipher, c) {
        cipher.type = null;
        cipher.name = c.name;
        cipher.notes = c.notes;
        cipher.fields = null;
        cipher.reprompt = c.reprompt;
        // Login props
        cipher.login_uri = null;
        cipher.login_username = null;
        cipher.login_password = null;
        cipher.login_totp = null;
        if (c.fields) {
            c.fields.forEach((f) => {
                if (!cipher.fields) {
                    cipher.fields = "";
                }
                else {
                    cipher.fields += "\n";
                }
                cipher.fields += (f.name || "") + ": " + f.value;
            });
        }
        switch (c.type) {
            case bw_CipherType.Login:
                cipher.type = "login";
                cipher.login_username = c.login.username;
                cipher.login_password = c.login.password;
                cipher.login_totp = c.login.totp;
                if (c.login.uris) {
                    cipher.login_uri = [];
                    c.login.uris.forEach((u) => {
                        cipher.login_uri.push(u.uri);
                    });
                }
                break;
            case bw_CipherType.SecureNote:
                cipher.type = "note";
                break;
            default:
                return;
        }
        return cipher;
    }
}

;// ../../libs/tools/export/vault-export/vault-export-core/src/services/org-vault-export.service.ts
var bw_org_vault_export_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










class bw_OrganizationVaultExportService extends bw_BaseVaultExportService {
    constructor(cipherService, apiService, pinService, keyService, encryptService, cryptoFunctionService, collectionService, kdfConfigService, accountService) {
        super(pinService, encryptService, cryptoFunctionService, kdfConfigService);
        this.cipherService = cipherService;
        this.apiService = apiService;
        this.keyService = keyService;
        this.collectionService = collectionService;
        this.accountService = accountService;
    }
    getPasswordProtectedExport(organizationId, password, onlyManagedCollections) {
        return bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
            const clearText = yield this.getOrganizationExport(organizationId, "json", onlyManagedCollections);
            return this.buildPasswordExport(clearText, password);
        });
    }
    getOrganizationExport(organizationId_1) {
        return bw_org_vault_export_service_awaiter(this, arguments, void 0, function* (organizationId, format = "csv", onlyManagedCollections) {
            if (bw_utils_Utils.isNullOrWhitespace(organizationId)) {
                throw new Error("OrganizationId must be set");
            }
            if (format === "encrypted_json") {
                return onlyManagedCollections
                    ? this.getEncryptedManagedExport(organizationId)
                    : this.getOrganizationEncryptedExport(organizationId);
            }
            return onlyManagedCollections
                ? this.getDecryptedManagedExport(organizationId, format)
                : this.getOrganizationDecryptedExport(organizationId, format);
        });
    }
    getOrganizationDecryptedExport(organizationId, format) {
        return bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
            const decCollections = [];
            const decCiphers = [];
            const promises = [];
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            promises.push(this.apiService.getOrganizationExport(organizationId).then((exportData) => {
                const exportPromises = [];
                if (exportData != null) {
                    if (exportData.collections != null && exportData.collections.length > 0) {
                        exportData.collections.forEach((c) => {
                            const collection = new bw_Collection(new bw_collection_data_CollectionData(c));
                            exportPromises.push((0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.activeUserOrgKeys$)
                                .then((keys) => collection.decrypt(keys[organizationId]))
                                .then((decCol) => {
                                decCollections.push(decCol);
                            }));
                        });
                    }
                    if (exportData.ciphers != null && exportData.ciphers.length > 0) {
                        exportData.ciphers
                            .filter((c) => c.deletedDate === null)
                            .forEach((c) => bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
                            const cipher = new bw_Cipher(new bw_CipherData(c));
                            exportPromises.push(this.cipherService
                                .getKeyForCipherKeyDecryption(cipher, activeUserId)
                                .then((key) => cipher.decrypt(key))
                                .then((decCipher) => {
                                decCiphers.push(decCipher);
                            }));
                        }));
                    }
                }
                return Promise.all(exportPromises);
            }));
            yield Promise.all(promises);
            if (format === "csv") {
                return this.buildCsvExport(decCollections, decCiphers);
            }
            return this.buildJsonExport(decCollections, decCiphers);
        });
    }
    getOrganizationEncryptedExport(organizationId) {
        return bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
            const collections = [];
            const ciphers = [];
            const promises = [];
            promises.push(this.apiService.getCollections(organizationId).then((c) => {
                if (c != null && c.data != null && c.data.length > 0) {
                    c.data.forEach((r) => {
                        const collection = new bw_Collection(new bw_collection_data_CollectionData(r));
                        collections.push(collection);
                    });
                }
            }));
            promises.push(this.apiService.getCiphersOrganization(organizationId).then((c) => {
                if (c != null && c.data != null && c.data.length > 0) {
                    c.data
                        .filter((item) => item.deletedDate === null)
                        .forEach((item) => {
                        const cipher = new bw_Cipher(new bw_CipherData(item));
                        ciphers.push(cipher);
                    });
                }
            }));
            yield Promise.all(promises);
            return this.BuildEncryptedExport(organizationId, collections, ciphers);
        });
    }
    getDecryptedManagedExport(organizationId, format) {
        return bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
            let decCiphers = [];
            let allDecCiphers = [];
            let decCollections = [];
            const promises = [];
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            promises.push(this.collectionService.getAllDecrypted().then((collections) => bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
                decCollections = collections.filter((c) => c.organizationId == organizationId && c.manage);
            })));
            promises.push(this.cipherService.getAllDecrypted(activeUserId).then((ciphers) => {
                allDecCiphers = ciphers;
            }));
            yield Promise.all(promises);
            decCiphers = allDecCiphers.filter((f) => f.deletedDate == null &&
                f.organizationId == organizationId &&
                decCollections.some((dC) => f.collectionIds.some((cId) => dC.id === cId)));
            if (format === "csv") {
                return this.buildCsvExport(decCollections, decCiphers);
            }
            return this.buildJsonExport(decCollections, decCiphers);
        });
    }
    getEncryptedManagedExport(organizationId) {
        return bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
            let encCiphers = [];
            let allCiphers = [];
            let encCollections = [];
            const promises = [];
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            promises.push(this.collectionService.getAll().then((collections) => {
                encCollections = collections.filter((c) => c.organizationId == organizationId && c.manage);
            }));
            promises.push(this.cipherService.getAll(activeUserId).then((ciphers) => {
                allCiphers = ciphers;
            }));
            yield Promise.all(promises);
            encCiphers = allCiphers.filter((f) => f.deletedDate == null &&
                f.organizationId == organizationId &&
                encCollections.some((eC) => f.collectionIds.some((cId) => eC.id === cId)));
            return this.BuildEncryptedExport(organizationId, encCollections, encCiphers);
        });
    }
    BuildEncryptedExport(organizationId, collections, ciphers) {
        return bw_org_vault_export_service_awaiter(this, void 0, void 0, function* () {
            const orgKey = yield this.keyService.getOrgKey(organizationId);
            const encKeyValidation = yield this.encryptService.encrypt(bw_utils_Utils.newGuid(), orgKey);
            const jsonDoc = {
                encrypted: true,
                encKeyValidation_DO_NOT_EDIT: encKeyValidation.encryptedString,
                collections: [],
                items: [],
            };
            collections.forEach((c) => {
                const collection = new bw_CollectionWithIdExport();
                collection.build(c);
                jsonDoc.collections.push(collection);
            });
            ciphers.forEach((c) => {
                const cipher = new bw_CipherWithIdExport();
                cipher.build(c);
                jsonDoc.items.push(cipher);
            });
            return JSON.stringify(jsonDoc, null, "  ");
        });
    }
    buildCsvExport(decCollections, decCiphers) {
        const collectionsMap = new Map();
        decCollections.forEach((c) => {
            collectionsMap.set(c.id, c);
        });
        const exportCiphers = [];
        decCiphers.forEach((c) => {
            // only export logins and secure notes
            if (c.type !== bw_CipherType.Login && c.type !== bw_CipherType.SecureNote) {
                return;
            }
            const cipher = {};
            cipher.collections = [];
            if (c.collectionIds != null) {
                cipher.collections = c.collectionIds
                    .filter((id) => collectionsMap.has(id))
                    .map((id) => collectionsMap.get(id).name);
            }
            this.buildCommonCipher(cipher, c);
            exportCiphers.push(cipher);
        });
        return bw_external_papaparse_namespaceObject.unparse(exportCiphers);
    }
    buildJsonExport(decCollections, decCiphers) {
        const jsonDoc = {
            encrypted: false,
            collections: [],
            items: [],
        };
        decCollections.forEach((c) => {
            const collection = new bw_CollectionWithIdExport();
            collection.build(c);
            jsonDoc.collections.push(collection);
        });
        decCiphers.forEach((c) => {
            const cipher = new bw_CipherWithIdExport();
            cipher.build(c);
            jsonDoc.items.push(cipher);
        });
        return JSON.stringify(jsonDoc, null, "  ");
    }
}

;// ../../libs/tools/export/vault-export/vault-export-core/src/services/individual-vault-export.service.ts
var bw_individual_vault_export_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







class bw_IndividualVaultExportService extends bw_BaseVaultExportService {
    constructor(folderService, cipherService, pinService, keyService, encryptService, cryptoFunctionService, kdfConfigService, accountService) {
        super(pinService, encryptService, cryptoFunctionService, kdfConfigService);
        this.folderService = folderService;
        this.cipherService = cipherService;
        this.keyService = keyService;
        this.accountService = accountService;
    }
    getExport() {
        return bw_individual_vault_export_service_awaiter(this, arguments, void 0, function* (format = "csv") {
            if (format === "encrypted_json") {
                return this.getEncryptedExport();
            }
            return this.getDecryptedExport(format);
        });
    }
    getPasswordProtectedExport(password) {
        return bw_individual_vault_export_service_awaiter(this, void 0, void 0, function* () {
            const clearText = yield this.getExport("json");
            return this.buildPasswordExport(clearText, password);
        });
    }
    getDecryptedExport(format) {
        return bw_individual_vault_export_service_awaiter(this, void 0, void 0, function* () {
            let decFolders = [];
            let decCiphers = [];
            const promises = [];
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            promises.push((0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.folderService.folderViews$(activeUserId)).then((folders) => {
                decFolders = folders;
            }));
            promises.push(this.cipherService.getAllDecrypted(activeUserId).then((ciphers) => {
                decCiphers = ciphers.filter((f) => f.deletedDate == null);
            }));
            yield Promise.all(promises);
            if (format === "csv") {
                return this.buildCsvExport(decFolders, decCiphers);
            }
            return this.buildJsonExport(decFolders, decCiphers);
        });
    }
    getEncryptedExport() {
        return bw_individual_vault_export_service_awaiter(this, void 0, void 0, function* () {
            let folders = [];
            let ciphers = [];
            const promises = [];
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            promises.push((0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.folderService.folders$(activeUserId)).then((f) => {
                folders = f;
            }));
            promises.push(this.cipherService.getAll(activeUserId).then((c) => {
                ciphers = c.filter((f) => f.deletedDate == null);
            }));
            yield Promise.all(promises);
            const userKey = yield this.keyService.getUserKeyWithLegacySupport(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId)));
            const encKeyValidation = yield this.encryptService.encrypt(bw_utils_Utils.newGuid(), userKey);
            const jsonDoc = {
                encrypted: true,
                encKeyValidation_DO_NOT_EDIT: encKeyValidation.encryptedString,
                folders: [],
                items: [],
            };
            folders.forEach((f) => {
                if (f.id == null) {
                    return;
                }
                const folder = new bw_FolderWithIdExport();
                folder.build(f);
                jsonDoc.folders.push(folder);
            });
            ciphers.forEach((c) => {
                if (c.organizationId != null) {
                    return;
                }
                const cipher = new bw_CipherWithIdExport();
                cipher.build(c);
                cipher.collectionIds = null;
                jsonDoc.items.push(cipher);
            });
            return JSON.stringify(jsonDoc, null, "  ");
        });
    }
    buildCsvExport(decFolders, decCiphers) {
        const foldersMap = new Map();
        decFolders.forEach((f) => {
            if (f.id != null) {
                foldersMap.set(f.id, f);
            }
        });
        const exportCiphers = [];
        decCiphers.forEach((c) => {
            // only export logins and secure notes
            if (c.type !== bw_CipherType.Login && c.type !== bw_CipherType.SecureNote) {
                return;
            }
            if (c.organizationId != null) {
                return;
            }
            const cipher = {};
            cipher.folder =
                c.folderId != null && foldersMap.has(c.folderId) ? foldersMap.get(c.folderId).name : null;
            cipher.favorite = c.favorite ? 1 : null;
            this.buildCommonCipher(cipher, c);
            exportCiphers.push(cipher);
        });
        return bw_external_papaparse_namespaceObject.unparse(exportCiphers);
    }
    buildJsonExport(decFolders, decCiphers) {
        const jsonDoc = {
            encrypted: false,
            folders: [],
            items: [],
        };
        decFolders.forEach((f) => {
            if (f.id == null) {
                return;
            }
            const folder = new bw_FolderWithIdExport();
            folder.build(f);
            jsonDoc.folders.push(folder);
        });
        decCiphers.forEach((c) => {
            if (c.organizationId != null) {
                return;
            }
            const cipher = new bw_CipherWithIdExport();
            cipher.build(c);
            cipher.collectionIds = null;
            jsonDoc.items.push(cipher);
        });
        return JSON.stringify(jsonDoc, null, "  ");
    }
}

;// ../../libs/tools/export/vault-export/vault-export-core/src/index.ts









;// ./src/tools/export.command.ts
var bw_export_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};







class bw_ExportCommand {
    constructor(exportService, policyService, eventCollectionService) {
        this.exportService = exportService;
        this.policyService = policyService;
        this.eventCollectionService = eventCollectionService;
    }
    run(options) {
        return bw_export_command_awaiter(this, void 0, void 0, function* () {
            var _a;
            if (options.organizationid == null &&
                (yield this.policyService.policyAppliesToUser(bw_policy_type_enum_PolicyType.DisablePersonalVaultExport))) {
                return bw_Response.badRequest("One or more organization policies prevents you from exporting your personal vault.");
            }
            let password = options.password;
            // has password and format is 'json' => should have the same behaviour as 'encrypted_json'
            // format is 'undefined' => Defaults to 'csv'
            // Any other case => returns the options.format
            const format = password && options.format == "json" ? "encrypted_json" : ((_a = options.format) !== null && _a !== void 0 ? _a : "csv");
            if (!this.isSupportedExportFormat(format)) {
                return bw_Response.badRequest(`'${format}' is not a supported export format. Supported formats: ${bw_EXPORT_FORMATS.join(", ")}.`);
            }
            if (options.organizationid != null && !bw_utils_Utils.isGuid(options.organizationid)) {
                return bw_Response.error("`" + options.organizationid + "` is not a GUID.");
            }
            let exportContent = null;
            try {
                if (format === "encrypted_json") {
                    password = yield this.promptPassword(password);
                }
                exportContent =
                    options.organizationid == null
                        ? yield this.exportService.getExport(format, password)
                        : yield this.exportService.getOrganizationExport(options.organizationid, format, password);
                const eventType = options.organizationid
                    ? bw_EventType.Organization_ClientExportedVault
                    : bw_EventType.User_ClientExportedVault;
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.eventCollectionService.collect(eventType, null, true, options.organizationid);
            }
            catch (e) {
                return bw_Response.error(e);
            }
            return yield this.saveFile(exportContent, options, format);
        });
    }
    saveFile(exportContent, options, format) {
        return bw_export_command_awaiter(this, void 0, void 0, function* () {
            try {
                const fileName = this.getFileName(format, options.organizationid != null ? "org" : null);
                return yield bw_CliUtils.saveResultToFile(exportContent, options.output, fileName);
            }
            catch (e) {
                return bw_Response.error(e.toString());
            }
        });
    }
    getFileName(format, prefix) {
        if (format === "encrypted_json") {
            if (prefix == null) {
                prefix = "encrypted";
            }
            else {
                prefix = "encrypted_" + prefix;
            }
            format = "json";
        }
        return this.exportService.getFileName(prefix, format);
    }
    promptPassword(password) {
        return bw_export_command_awaiter(this, void 0, void 0, function* () {
            // boolean => flag set with no value, we need to prompt for password
            // string => flag set with value, use this value for password
            // undefined/null/false => account protect, not password, no password needed
            if (typeof password === "string") {
                return password;
            }
            else if (password) {
                const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                    output: process.stderr,
                })({
                    type: "password",
                    name: "password",
                    message: "Export file password:",
                });
                return answer.password;
            }
            return null;
        });
    }
    isSupportedExportFormat(format) {
        return bw_EXPORT_FORMATS.includes(format);
    }
}

;// ../../libs/common/src/admin-console/abstractions/organization/organization.service.abstraction.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

function bw_canAccessVaultTab(org) {
    return org.canViewAllCollections;
}
function bw_canAccessSettingsTab(org) {
    return (org.isOwner ||
        org.canManagePolicies ||
        org.canManageSso ||
        org.canManageScim ||
        org.canAccessImport ||
        org.canAccessExport ||
        org.canManageDeviceApprovals);
}
function bw_canAccessMembersTab(org) {
    return org.canManageUsers || org.canManageUsersPassword;
}
function bw_canAccessGroupsTab(org) {
    return org.canManageGroups;
}
function bw_canAccessReportingTab(org) {
    return org.canAccessReports || org.canAccessEventLogs;
}
function bw_canAccessBillingTab(org) {
    return org.isOwner;
}
function bw_canAccessOrgAdmin(org) {
    // Admin console can only be accessed by Owners for disabled organizations
    if (!org.enabled && !org.isOwner) {
        return false;
    }
    return (bw_canAccessMembersTab(org) ||
        bw_canAccessGroupsTab(org) ||
        bw_canAccessReportingTab(org) ||
        bw_canAccessBillingTab(org) ||
        bw_canAccessSettingsTab(org) ||
        bw_canAccessVaultTab(org));
}
function bw_getOrganizationById(id) {
    return (0,bw_external_rxjs_namespaceObject.map)((orgs) => orgs.find((o) => o.id === id));
}
/**
 * Publishes an observable stream of organizations. This service is meant to
 * be used widely across Bitwarden as the primary way of fetching organizations.
 * Risky operations like updates are isolated to the
 * internal extension `InternalOrganizationServiceAbstraction`.
 */
class bw_OrganizationService {
}
/**
 * Big scary buttons that **update** organization state. These should only be
 * called from within admin-console scoped code. Extends the base
 * `OrganizationService` for easy access to `get` calls.
 * @internal
 */
class bw_InternalOrganizationServiceAbstraction extends (/* unused pure expression or super */ null && (bw_OrganizationService)) {
}

;// ./src/tools/import.command.ts
var bw_import_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};







class bw_ImportCommand {
    constructor(importService, organizationService, syncService, accountService) {
        this.importService = importService;
        this.organizationService = organizationService;
        this.syncService = syncService;
        this.accountService = accountService;
    }
    run(format, filepath, options) {
        return bw_import_command_awaiter(this, void 0, void 0, function* () {
            const organizationId = options.organizationid;
            if (organizationId != null) {
                const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
                if (!userId) {
                    return bw_Response.badRequest("No user found.");
                }
                const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService.organizations$(userId).pipe(bw_getOrganizationById(organizationId)));
                if (organization == null) {
                    return bw_Response.badRequest(`You do not belong to an organization with the ID of ${organizationId}. Check the organization ID and sync your vault.`);
                }
                if (!organization.canAccessImport) {
                    return bw_Response.badRequest("You are not authorized to import into the provided organization.");
                }
            }
            if (options.formats || false) {
                return yield this.list();
            }
            else {
                return yield this.import(format, filepath, organizationId);
            }
        });
    }
    import(format, filepath, organizationId) {
        return bw_import_command_awaiter(this, void 0, void 0, function* () {
            if (format == null) {
                return bw_Response.badRequest("`format` was not provided.");
            }
            if (filepath == null || filepath === "") {
                return bw_Response.badRequest("`filepath` was not provided.");
            }
            const promptForPassword_callback = () => bw_import_command_awaiter(this, void 0, void 0, function* () {
                return yield this.promptPassword();
            });
            const importer = yield this.importService.getImporter(format, promptForPassword_callback, organizationId);
            if (importer === null) {
                return bw_Response.badRequest("Proper importer type required.");
            }
            try {
                let contents;
                if (format === "1password1pux" && filepath.endsWith(".1pux")) {
                    contents = yield bw_CliUtils.extractZipContent(filepath, "export.data");
                }
                else if (format === "protonpass" && filepath.endsWith(".zip")) {
                    contents = yield bw_CliUtils.extractZipContent(filepath, "Proton Pass/data.json");
                }
                else {
                    contents = yield bw_CliUtils.readFile(filepath);
                }
                if (contents === null || contents === "") {
                    return bw_Response.badRequest("Import file was empty.");
                }
                const response = yield this.importService.import(importer, contents, organizationId);
                if (response.success) {
                    // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                    // eslint-disable-next-line @typescript-eslint/no-floating-promises
                    this.syncService.fullSync(true);
                    return bw_Response.success(new bw_MessageResponse("Imported " + filepath, null));
                }
            }
            catch (err) {
                if (err.message) {
                    return bw_Response.badRequest(err.message);
                }
                return bw_Response.badRequest(err);
            }
        });
    }
    list() {
        return bw_import_command_awaiter(this, void 0, void 0, function* () {
            const options = this.importService
                .getImportOptions()
                .sort((a, b) => {
                return a.id < b.id ? -1 : a.id > b.id ? 1 : 0;
            })
                .map((option) => option.id)
                .join("\n");
            const res = new bw_MessageResponse("Supported input formats:", options);
            res.raw = options;
            return bw_Response.success(res);
        });
    }
    promptPassword() {
        return bw_import_command_awaiter(this, void 0, void 0, function* () {
            const answer = yield bw_external_inquirer_namespaceObject.createPromptModule({
                output: process.stderr,
            })({
                type: "password",
                name: "password",
                message: "Import file password:",
            });
            return answer.password;
        });
    }
}

;// ./src/vault/create.command.ts
var bw_vault_create_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore















class bw_CreateCommand {
    constructor(cipherService, folderService, keyService, encryptService, apiService, folderApiService, accountProfileService, organizationService, accountService) {
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.apiService = apiService;
        this.folderApiService = folderApiService;
        this.accountProfileService = accountProfileService;
        this.organizationService = organizationService;
        this.accountService = accountService;
    }
    run(object_1, requestJson_1, cmdOptions_1) {
        return bw_vault_create_command_awaiter(this, arguments, void 0, function* (object, requestJson, cmdOptions, additionalData = null) {
            let req = null;
            if (object !== "attachment") {
                if (process.env.BW_SERVE !== "true" && (requestJson == null || requestJson === "")) {
                    requestJson = yield bw_CliUtils.readStdin();
                }
                if (requestJson == null || requestJson === "") {
                    return bw_Response.badRequest("`requestJson` was not provided.");
                }
                if (typeof requestJson !== "string") {
                    req = requestJson;
                }
                else {
                    try {
                        const reqJson = Buffer.from(requestJson, "base64").toString();
                        req = JSON.parse(reqJson);
                        // FIXME: Remove when updating file. Eslint update
                        // eslint-disable-next-line @typescript-eslint/no-unused-vars
                    }
                    catch (e) {
                        return bw_Response.badRequest("Error parsing the encoded request data.");
                    }
                }
            }
            const normalizedOptions = new bw_vault_create_command_Options(cmdOptions);
            switch (object.toLowerCase()) {
                case "item":
                    return yield this.createCipher(req);
                case "attachment":
                    return yield this.createAttachment(normalizedOptions, additionalData);
                case "folder":
                    return yield this.createFolder(req);
                case "org-collection":
                    return yield this.createOrganizationCollection(req, normalizedOptions);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    createCipher(req) {
        return bw_vault_create_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const cipher = yield this.cipherService.encrypt(bw_CipherExport.toView(req), activeUserId);
            try {
                const newCipher = yield this.cipherService.createWithServer(cipher);
                const decCipher = yield newCipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(newCipher, activeUserId));
                const res = new bw_CipherResponse(decCipher);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    createAttachment(options, additionalData) {
        return bw_vault_create_command_awaiter(this, void 0, void 0, function* () {
            if (options.itemId == null || options.itemId === "") {
                return bw_Response.badRequest("`itemid` option is required.");
            }
            let fileBuf = null;
            let fileName = null;
            if (process.env.BW_SERVE === "true") {
                fileBuf = additionalData.fileBuffer;
                fileName = additionalData.fileName;
            }
            else {
                if (options.file == null || options.file === "") {
                    return bw_Response.badRequest("`file` option is required.");
                }
                const filePath = bw_external_path_namespaceObject.resolve(options.file);
                if (!bw_external_fs_namespaceObject.existsSync(options.file)) {
                    return bw_Response.badRequest("Cannot find file at " + filePath);
                }
                fileBuf = bw_external_fs_namespaceObject.readFileSync(filePath);
                fileName = bw_external_path_namespaceObject.basename(filePath);
            }
            if (fileBuf == null) {
                return bw_Response.badRequest("File not provided.");
            }
            if (fileName == null || fileName.trim() === "") {
                return bw_Response.badRequest("File name not provided.");
            }
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const itemId = options.itemId.toLowerCase();
            const cipher = yield this.cipherService.get(itemId, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            const canAccessPremium = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountProfileService.hasPremiumFromAnySource$(activeUserId));
            if (cipher.organizationId == null && !canAccessPremium) {
                return bw_Response.error("Premium status is required to use this feature.");
            }
            const userKey = yield this.keyService.getUserKey();
            if (userKey == null) {
                return bw_Response.error("You must update your encryption key before you can use this feature. " +
                    "See https://help.bitwarden.com/article/update-encryption-key/");
            }
            try {
                const updatedCipher = yield this.cipherService.saveAttachmentRawWithServer(cipher, fileName, new Uint8Array(fileBuf).buffer, activeUserId);
                const decCipher = yield updatedCipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(updatedCipher, activeUserId));
                return bw_Response.success(new bw_CipherResponse(decCipher));
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    createFolder(req) {
        return bw_vault_create_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const userKey = yield this.keyService.getUserKeyWithLegacySupport(activeUserId);
            const folder = yield this.folderService.encrypt(bw_FolderExport.toView(req), userKey);
            try {
                yield this.folderApiService.save(folder, activeUserId);
                const newFolder = yield this.folderService.get(folder.id, activeUserId);
                const decFolder = yield newFolder.decrypt();
                const res = new bw_FolderResponse(decFolder);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    createOrganizationCollection(req, options) {
        return bw_vault_create_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("`organizationid` option is required.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            if (options.organizationId !== req.organizationId) {
                return bw_Response.badRequest("`organizationid` option does not match request object.");
            }
            try {
                const orgKey = yield this.keyService.getOrgKey(req.organizationId);
                if (orgKey == null) {
                    throw new Error("No encryption key for this organization.");
                }
                const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
                if (!userId) {
                    return bw_Response.badRequest("No user found.");
                }
                const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                    .organizations$(userId)
                    .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations.find((o) => o.id === req.organizationId))));
                const currentOrgUserId = organization.organizationUserId;
                const groups = req.groups == null
                    ? null
                    : req.groups.map((g) => new bw_selection_read_only_request_SelectionReadOnlyRequest(g.id, g.readOnly, g.hidePasswords, g.manage));
                const users = req.users == null
                    ? [new bw_selection_read_only_request_SelectionReadOnlyRequest(currentOrgUserId, false, false, true)]
                    : req.users.map((u) => new bw_selection_read_only_request_SelectionReadOnlyRequest(u.id, u.readOnly, u.hidePasswords, u.manage));
                const request = new bw_collection_request_CollectionRequest();
                request.name = (yield this.encryptService.encrypt(req.name, orgKey)).encryptedString;
                request.externalId = req.externalId;
                request.groups = groups;
                request.users = users;
                const response = yield this.apiService.postCollection(req.organizationId, request);
                const view = bw_CollectionExport.toView(req);
                view.id = response.id;
                const res = new bw_OrganizationCollectionResponse(view, groups, users);
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}
class bw_vault_create_command_Options {
    constructor(passedOptions) {
        this.organizationId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationId);
        this.itemId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemId);
        this.file = passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.file;
    }
}

;// ./src/vault/delete.command.ts
var bw_vault_delete_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_DeleteCommand {
    constructor(cipherService, folderService, apiService, folderApiService, accountProfileService, cipherAuthorizationService, accountService) {
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.apiService = apiService;
        this.folderApiService = folderApiService;
        this.accountProfileService = accountProfileService;
        this.cipherAuthorizationService = cipherAuthorizationService;
        this.accountService = accountService;
    }
    run(object, id, cmdOptions) {
        return bw_vault_delete_command_awaiter(this, void 0, void 0, function* () {
            if (id != null) {
                id = id.toLowerCase();
            }
            const normalizedOptions = new bw_delete_command_Options(cmdOptions);
            switch (object.toLowerCase()) {
                case "item":
                    return yield this.deleteCipher(id, normalizedOptions);
                case "attachment":
                    return yield this.deleteAttachment(id, normalizedOptions);
                case "folder":
                    return yield this.deleteFolder(id);
                case "org-collection":
                    return yield this.deleteOrganizationCollection(id, normalizedOptions);
                default:
                    return bw_Response.badRequest("Unknown object.");
            }
        });
    }
    deleteCipher(id, options) {
        return bw_vault_delete_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const cipher = yield this.cipherService.get(id, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            const canDeleteCipher = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.cipherAuthorizationService.canDeleteCipher$(cipher));
            if (!canDeleteCipher) {
                return bw_Response.error("You do not have permission to delete this item.");
            }
            try {
                if (options.permanent) {
                    yield this.cipherService.deleteWithServer(id, activeUserId);
                }
                else {
                    yield this.cipherService.softDeleteWithServer(id, activeUserId);
                }
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    deleteAttachment(id, options) {
        return bw_vault_delete_command_awaiter(this, void 0, void 0, function* () {
            if (options.itemId == null || options.itemId === "") {
                return bw_Response.badRequest("`itemid` option is required.");
            }
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const itemId = options.itemId.toLowerCase();
            const cipher = yield this.cipherService.get(itemId, activeUserId);
            if (cipher == null) {
                return bw_Response.notFound();
            }
            if (cipher.attachments == null || cipher.attachments.length === 0) {
                return bw_Response.error("No attachments available for this item.");
            }
            const attachments = cipher.attachments.filter((a) => a.id.toLowerCase() === id);
            if (attachments.length === 0) {
                return bw_Response.error("Attachment `" + id + "` was not found.");
            }
            const canAccessPremium = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountProfileService.hasPremiumFromAnySource$(activeUserId));
            if (cipher.organizationId == null && !canAccessPremium) {
                return bw_Response.error("Premium status is required to use this feature.");
            }
            try {
                yield this.cipherService.deleteAttachmentWithServer(cipher.id, attachments[0].id, activeUserId);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    deleteFolder(id) {
        return bw_vault_delete_command_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe(bw_getUserId));
            const folder = yield this.folderService.getFromState(id, activeUserId);
            if (folder == null) {
                return bw_Response.notFound();
            }
            try {
                yield this.folderApiService.delete(id, activeUserId);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    deleteOrganizationCollection(id, options) {
        return bw_vault_delete_command_awaiter(this, void 0, void 0, function* () {
            if (options.organizationId == null || options.organizationId === "") {
                return bw_Response.badRequest("`organizationid` options is required.");
            }
            if (!bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            if (!bw_utils_Utils.isGuid(options.organizationId)) {
                return bw_Response.badRequest("`" + options.organizationId + "` is not a GUID.");
            }
            try {
                yield this.apiService.deleteCollection(options.organizationId, id);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
}
class bw_delete_command_Options {
    constructor(passedOptions) {
        this.organizationId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.organizationId);
        this.itemId = (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemid) || (passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.itemId);
        this.permanent = bw_CliUtils.convertBooleanOption(passedOptions === null || passedOptions === void 0 ? void 0 : passedOptions.permanent);
    }
}

;// ./src/vault.program.ts
var bw_vault_program_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore














const bw_vault_program_writeLn = bw_CliUtils.writeLn;
class bw_VaultProgram extends bw_BaseProgram {
    register() {
        bw_external_commander_namespaceObject.program
            .addCommand(this.listCommand())
            .addCommand(this.getCommand())
            .addCommand(this.createCommand())
            .addCommand(this.editCommand())
            .addCommand(this.deleteCommand())
            .addCommand(this.restoreCommand())
            .addCommand(this.shareCommand("move", false))
            .addCommand(this.confirmCommand())
            .addCommand(this.importCommand())
            .addCommand(this.exportCommand())
            .addCommand(this.shareCommand("share", true));
    }
    validateObject(requestedObject, validObjects) {
        let success = true;
        if (!validObjects.includes(requestedObject)) {
            success = false;
            this.processResponse(bw_Response.badRequest('Unknown object "' +
                requestedObject +
                '". Allowed objects are ' +
                validObjects.join(", ") +
                "."));
        }
        return success;
    }
    listCommand() {
        const listObjects = [
            "items",
            "folders",
            "collections",
            "org-collections",
            "org-members",
            "organizations",
        ];
        return new bw_external_commander_namespaceObject.Command("list")
            .argument("<object>", "Valid objects are: " + listObjects.join(", "))
            .description("List an array of objects from the vault.")
            .option("--search <search>", "Perform a search on the listed objects.")
            .option("--url <url>", "Filter items of type login with a url-match search.")
            .option("--folderid <folderid>", "Filter items by folder id.")
            .option("--collectionid <collectionid>", "Filter items by collection id.")
            .option("--organizationid <organizationid>", "Filter items or collections by organization id.")
            .option("--trash", "Filter items that are deleted and in the trash.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Notes:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    Combining search with a filter performs a logical AND operation.");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    Combining multiple filters performs a logical OR operation.");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw list items");
            bw_vault_program_writeLn("    bw list items --folderid 60556c31-e649-4b5d-8daf-fc1c391a1bf2");
            bw_vault_program_writeLn("    bw list items --search google --folderid 60556c31-e649-4b5d-8daf-fc1c391a1bf2");
            bw_vault_program_writeLn("    bw list items --url https://google.com");
            bw_vault_program_writeLn("    bw list items --folderid null");
            bw_vault_program_writeLn("    bw list items --organizationid notnull");
            bw_vault_program_writeLn("    bw list items --folderid 60556c31-e649-4b5d-8daf-fc1c391a1bf2 --organizationid notnull");
            bw_vault_program_writeLn("    bw list items --trash");
            bw_vault_program_writeLn("    bw list folders --search email");
            bw_vault_program_writeLn("    bw list org-members --organizationid 60556c31-e649-4b5d-8daf-fc1c391a1bf2");
            bw_vault_program_writeLn("", true);
        })
            .action((object, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, listObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_ListCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.collectionService, this.serviceContainer.organizationService, this.serviceContainer.searchService, this.serviceContainer.organizationUserApiService, this.serviceContainer.apiService, this.serviceContainer.eventCollectionService, this.serviceContainer.accountService);
            const response = yield command.run(object, cmd);
            this.processResponse(response);
        }));
    }
    getCommand() {
        const getObjects = [
            "item",
            "username",
            "password",
            "uri",
            "totp",
            "notes",
            "exposed",
            "attachment",
            "folder",
            "collection",
            "org-collection",
            "organization",
            "template",
            "fingerprint",
            "send",
        ];
        return new bw_external_commander_namespaceObject.Command("get")
            .argument("<object>", "Valid objects are: " + getObjects.join(", "))
            .argument("<id>", "Search term or object's globally unique `id`.")
            .description("Get an object from the vault.")
            .option("--itemid <itemid>", "Attachment's item id.")
            .option("--output <output>", "Output directory or filename for attachment.")
            .option("--organizationid <organizationid>", "Organization id for an organization object.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  If raw output is specified and no output filename or directory is given for");
            bw_vault_program_writeLn("  an attachment query, the attachment content is written to stdout.");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw get item 99ee88d2-6046-4ea7-92c2-acac464b1412");
            bw_vault_program_writeLn("    bw get password https://google.com");
            bw_vault_program_writeLn("    bw get totp google.com");
            bw_vault_program_writeLn("    bw get notes google.com");
            bw_vault_program_writeLn("    bw get exposed yahoo.com");
            bw_vault_program_writeLn("    bw get attachment b857igwl1dzrs2 --itemid 99ee88d2-6046-4ea7-92c2-acac464b1412 " +
                "--output ./photo.jpg");
            bw_vault_program_writeLn("    bw get attachment photo.jpg --itemid 99ee88d2-6046-4ea7-92c2-acac464b1412 --raw");
            bw_vault_program_writeLn("    bw get folder email");
            bw_vault_program_writeLn("    bw get template folder");
            bw_vault_program_writeLn("", true);
        })
            .action((object, id, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, getObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_GetCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.collectionService, this.serviceContainer.totpService, this.serviceContainer.auditService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.searchService, this.serviceContainer.apiService, this.serviceContainer.organizationService, this.serviceContainer.eventCollectionService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
            const response = yield command.run(object, id, cmd);
            this.processResponse(response);
        }));
    }
    createCommand() {
        const createObjects = ["item", "attachment", "folder", "org-collection"];
        return new bw_external_commander_namespaceObject.Command("create")
            .argument("<object>", "Valid objects are: " + createObjects.join(", "))
            .argument("[encodedJson]", "Encoded json of the object to create. Can also be piped into stdin.")
            .description("Create an object in the vault.")
            .option("--file <file>", "Path to file for attachment.")
            .option("--itemid <itemid>", "Attachment's item id.")
            .option("--organizationid <organizationid>", "Organization id for an organization object.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw create folder eyJuYW1lIjoiTXkgRm9sZGVyIn0K");
            bw_vault_program_writeLn("    echo 'eyJuYW1lIjoiTXkgRm9sZGVyIn0K' | bw create folder");
            bw_vault_program_writeLn("    bw create attachment --file ./myfile.csv " +
                "--itemid 16b15b89-65b3-4639-ad2a-95052a6d8f66");
            bw_vault_program_writeLn("", true);
        })
            .action((object, encodedJson, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, createObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_CreateCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.apiService, this.serviceContainer.folderApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.organizationService, this.serviceContainer.accountService);
            const response = yield command.run(object, encodedJson, cmd);
            this.processResponse(response);
        }));
    }
    editCommand() {
        const editObjects = ["item", "item-collections", "folder", "org-collection"];
        return new bw_external_commander_namespaceObject.Command("edit")
            .argument("<object>", "Valid objects are: " + editObjects.join(", "))
            .argument("<id>", "Object's globally unique `id`.")
            .argument("[encodedJson]", "Encoded json of the object to create. Can also be piped into stdin.")
            .description("Edit an object from the vault.")
            .option("--organizationid <organizationid>", "Organization id for an organization object.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw edit folder 5cdfbd80-d99f-409b-915b-f4c5d0241b02 eyJuYW1lIjoiTXkgRm9sZGVyMiJ9Cg==");
            bw_vault_program_writeLn("    echo 'eyJuYW1lIjoiTXkgRm9sZGVyMiJ9Cg==' | " +
                "bw edit folder 5cdfbd80-d99f-409b-915b-f4c5d0241b02");
            bw_vault_program_writeLn("    bw edit item-collections 78307355-fd25-416b-88b8-b33fd0e88c82 " +
                "WyI5NzQwNTNkMC0zYjMzLTRiOTgtODg2ZS1mZWNmNWM4ZGJhOTYiXQ==");
            bw_vault_program_writeLn("", true);
        })
            .action((object, id, encodedJson, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, editObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_EditCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.apiService, this.serviceContainer.folderApiService, this.serviceContainer.accountService);
            const response = yield command.run(object, id, encodedJson, cmd);
            this.processResponse(response);
        }));
    }
    deleteCommand() {
        const deleteObjects = ["item", "attachment", "folder", "org-collection"];
        return new bw_external_commander_namespaceObject.Command("delete")
            .argument("<object>", "Valid objects are: " + deleteObjects.join(", "))
            .argument("<id>", "Object's globally unique `id`.")
            .description("Delete an object from the vault.")
            .option("--itemid <itemid>", "Attachment's item id.")
            .option("--organizationid <organizationid>", "Organization id for an organization object.")
            .option("-p, --permanent", "Permanently deletes the item instead of soft-deleting it (item only).")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw delete item 7063feab-4b10-472e-b64c-785e2b870b92");
            bw_vault_program_writeLn("    bw delete item 89c21cd2-fab0-4f69-8c6e-ab8a0168f69a --permanent");
            bw_vault_program_writeLn("    bw delete folder 5cdfbd80-d99f-409b-915b-f4c5d0241b02");
            bw_vault_program_writeLn("    bw delete attachment b857igwl1dzrs2 --itemid 310d5ffd-e9a2-4451-af87-ea054dce0f78");
            bw_vault_program_writeLn("", true);
        })
            .action((object, id, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, deleteObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_DeleteCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.apiService, this.serviceContainer.folderApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.cipherAuthorizationService, this.serviceContainer.accountService);
            const response = yield command.run(object, id, cmd);
            this.processResponse(response);
        }));
    }
    restoreCommand() {
        const restoreObjects = ["item"];
        return new bw_external_commander_namespaceObject.Command("restore")
            .argument("<object>", "Valid objects are: " + restoreObjects.join(", "))
            .argument("<id>", "Object's globally unique `id`.")
            .description("Restores an object from the trash.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw restore item 7063feab-4b10-472e-b64c-785e2b870b92");
            bw_vault_program_writeLn("", true);
        })
            .action((object, id, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, restoreObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_RestoreCommand(this.serviceContainer.cipherService, this.serviceContainer.accountService);
            const response = yield command.run(object, id);
            this.processResponse(response);
        }));
    }
    shareCommand(commandName, deprecated) {
        return new bw_external_commander_namespaceObject.Command(commandName)
            .argument("<id>", "Object's globally unique `id`.")
            .argument("<organizationId>", "Organization's globally unique `id`.")
            .argument("[encodedJson]", "Encoded json of an array of collection ids. Can also be piped into stdin.")
            .description((deprecated ? "--DEPRECATED-- " : "") + "Move an item to an organization.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw " +
                commandName +
                " 4af958ce-96a7-45d9-beed-1e70fabaa27a " +
                "6d82949b-b44d-468a-adae-3f3bacb0ea32 WyI5NzQwNTNkMC0zYjMzLTRiOTgtODg2ZS1mZWNmNWM4ZGJhOTYiXQ==");
            bw_vault_program_writeLn("    echo '[\"974053d0-3b33-4b98-886e-fecf5c8dba96\"]' | bw encode | " +
                "bw " +
                commandName +
                " 4af958ce-96a7-45d9-beed-1e70fabaa27a 6d82949b-b44d-468a-adae-3f3bacb0ea32");
            if (deprecated) {
                bw_vault_program_writeLn("");
                bw_vault_program_writeLn('--DEPRECATED See "bw move" for the current implementation--');
            }
            bw_vault_program_writeLn("", true);
        })
            .action((id, organizationId, encodedJson, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const command = new bw_ShareCommand(this.serviceContainer.cipherService, this.serviceContainer.accountService);
            const response = yield command.run(id, organizationId, encodedJson);
            this.processResponse(response);
        }));
    }
    confirmCommand() {
        const confirmObjects = ["org-member"];
        return new bw_external_commander_namespaceObject.Command("confirm")
            .argument("<object>", "Valid objects are: " + confirmObjects.join(", "))
            .argument("<id>", "Object's globally unique `id`.")
            .description("Confirm an object to the organization.")
            .option("--organizationid <organizationid>", "Organization id for an organization object.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw confirm org-member 7063feab-4b10-472e-b64c-785e2b870b92 " +
                "--organizationid 310d5ffd-e9a2-4451-af87-ea054dce0f78");
            bw_vault_program_writeLn("", true);
        })
            .action((object, id, cmd) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            if (!this.validateObject(object, confirmObjects)) {
                return;
            }
            yield this.exitIfLocked();
            const command = new bw_ConfirmCommand(this.serviceContainer.apiService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.organizationUserApiService);
            const response = yield command.run(object, id, cmd);
            this.processResponse(response);
        }));
    }
    importCommand() {
        return new bw_external_commander_namespaceObject.Command("import")
            .argument("[format]", "The format of [input]")
            .argument("[input]", "Filepath to data to import")
            .description("Import vault data from a file.")
            .option("--formats", "List formats")
            .option("--organizationid <organizationid>", "ID of the organization to import to.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw import --formats");
            bw_vault_program_writeLn("    bw import bitwardencsv ./from/source.csv");
            bw_vault_program_writeLn("    bw import keepass2xml keepass_backup.xml");
            bw_vault_program_writeLn("    bw import --organizationid cf14adc3-aca5-4573-890a-f6fa231436d9 keepass2xml keepass_backup.xml");
        })
            .action((format, filepath, options) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const command = new bw_ImportCommand(this.serviceContainer.importService, this.serviceContainer.organizationService, this.serviceContainer.syncService, this.serviceContainer.accountService);
            const response = yield command.run(format, filepath, options);
            this.processResponse(response);
        }));
    }
    exportCommand() {
        return new bw_external_commander_namespaceObject.Command("export")
            .description("Export vault data to a CSV or JSON file.")
            .option("--output <output>", "Output directory or filename.")
            .option("--format <format>", "Export file format.")
            .option("--password [password]", "Use password to encrypt instead of your Bitwarden account encryption key. Only applies to the encrypted_json format.")
            .option("--organizationid <organizationid>", "Organization id for an organization.")
            .on("--help", () => {
            bw_vault_program_writeLn("\n  Notes:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    Valid formats are `csv`, `json`, and `encrypted_json`. Default format is `csv`.");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    If --raw option is specified and no output filename or directory is given, the");
            bw_vault_program_writeLn("    result is written to stdout.");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("  Examples:");
            bw_vault_program_writeLn("");
            bw_vault_program_writeLn("    bw export");
            bw_vault_program_writeLn("    bw --raw export");
            bw_vault_program_writeLn("    bw export myPassword321");
            bw_vault_program_writeLn("    bw export myPassword321 --format json");
            bw_vault_program_writeLn("    bw export --output ./exp/bw.csv");
            bw_vault_program_writeLn("    bw export myPassword321 --output bw.json --format json");
            bw_vault_program_writeLn("    bw export myPassword321 --organizationid 7063feab-4b10-472e-b64c-785e2b870b92");
            bw_vault_program_writeLn("", true);
        })
            .action((options) => bw_vault_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const command = new bw_ExportCommand(this.serviceContainer.exportService, this.serviceContainer.policyService, this.serviceContainer.eventCollectionService);
            const response = yield command.run(options);
            this.processResponse(response);
        }));
    }
}

;// ./src/register-oss-programs.ts
var bw_register_oss_programs_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



/**
 * All OSS licensed programs should be registered here.
 * @example
 * const myProgram = new myProgram(serviceContainer);
 * myProgram.register();
 * @param serviceContainer A class that instantiates services and makes them available for dependency injection
 */
function bw_registerOssPrograms(serviceContainer) {
    return bw_register_oss_programs_awaiter(this, void 0, void 0, function* () {
        const program = new bw_Program(serviceContainer);
        yield program.register();
        const vaultProgram = new bw_VaultProgram(serviceContainer);
        vaultProgram.register();
        const sendProgram = new bw_SendProgram(serviceContainer);
        sendProgram.register();
    });
}

;// external "@koa/router"
const bw_router_namespaceObject = require("@koa/router");
;// external "koa"
const bw_external_koa_namespaceObject = require("koa");
;// external "koa-bodyparser"
const bw_external_koa_bodyparser_namespaceObject = require("koa-bodyparser");
;// external "koa-json"
const bw_external_koa_json_namespaceObject = require("koa-json");
;// ./src/commands/serve.command.ts
var bw_serve_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_ServeCommand {
    constructor(serviceContainer, serveConfigurator) {
        this.serviceContainer = serviceContainer;
        this.serveConfigurator = serveConfigurator;
    }
    run(options) {
        return bw_serve_command_awaiter(this, void 0, void 0, function* () {
            const protectOrigin = !options.disableOriginProtection;
            const port = options.port || 8087;
            const hostname = options.hostname || "localhost";
            this.serviceContainer.logService.info(`Starting server on ${hostname}:${port} with ${protectOrigin ? "origin protection" : "no origin protection"}`);
            const server = new bw_external_koa_namespaceObject();
            const router = new bw_router_namespaceObject();
            process.env.BW_SERVE = "true";
            process.env.BW_NOINTERACTION = "true";
            server
                .use((ctx, next) => bw_serve_command_awaiter(this, void 0, void 0, function* () {
                if (protectOrigin && ctx.headers.origin != undefined) {
                    ctx.status = 403;
                    this.serviceContainer.logService.warning(`Blocking request from "${bw_utils_Utils.isNullOrEmpty(ctx.headers.origin)
                        ? "(Origin header value missing)"
                        : ctx.headers.origin}"`);
                    return;
                }
                yield next();
            }))
                .use(bw_external_koa_bodyparser_namespaceObject())
                .use(bw_external_koa_json_namespaceObject({ pretty: false, param: "pretty" }));
            this.serveConfigurator.configureRouter(router);
            server
                .use(router.routes())
                .use(router.allowedMethods())
                .listen(port, hostname === "all" ? null : hostname, () => {
                this.serviceContainer.logService.info("Listening on " + hostname + ":" + port);
            });
        });
    }
}

;// ./src/serve.program.ts
var bw_serve_program_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




const bw_serve_program_writeLn = bw_CliUtils.writeLn;
class bw_ServeProgram extends bw_BaseProgram {
    constructor(serviceContainer, configurator) {
        super(serviceContainer);
        this.configurator = configurator;
    }
    register() {
        bw_external_commander_namespaceObject.program
            .command("serve")
            .description("Start a RESTful API webserver.")
            .option("--hostname <hostname>", "The hostname to bind your API webserver to.")
            .option("--port <port>", "The port to run your API webserver on.")
            .option("--disable-origin-protection", "If set, allows requests with origin header. Warning, this option exists for backwards compatibility reasons and exposes your environment to known CSRF attacks.")
            .on("--help", () => {
            bw_serve_program_writeLn("\n  Notes:");
            bw_serve_program_writeLn("");
            bw_serve_program_writeLn("    Default hostname is `localhost`.");
            bw_serve_program_writeLn("    Use hostname `all` for no hostname binding.");
            bw_serve_program_writeLn("    Default port is `8087`.");
            bw_serve_program_writeLn("");
            bw_serve_program_writeLn("  Examples:");
            bw_serve_program_writeLn("");
            bw_serve_program_writeLn("    bw serve");
            bw_serve_program_writeLn("    bw serve --port 8080");
            bw_serve_program_writeLn("    bw serve --hostname bwapi.mydomain.com --port 80");
            bw_serve_program_writeLn("", true);
        })
            .action((cmd) => bw_serve_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfNotAuthed();
            const command = new bw_ServeCommand(this.serviceContainer, this.configurator);
            yield command.run(cmd);
        }));
    }
}

;// external "@koa/multer"
const bw_multer_namespaceObject = require("@koa/multer");
;// ./src/tools/send/index.ts


;// ./src/oss-serve-configurator.ts
var bw_oss_serve_configurator_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

















class bw_OssServeConfigurator {
    constructor(serviceContainer) {
        this.serviceContainer = serviceContainer;
        this.getCommand = new bw_GetCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.collectionService, this.serviceContainer.totpService, this.serviceContainer.auditService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.searchService, this.serviceContainer.apiService, this.serviceContainer.organizationService, this.serviceContainer.eventCollectionService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
        this.listCommand = new bw_ListCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.collectionService, this.serviceContainer.organizationService, this.serviceContainer.searchService, this.serviceContainer.organizationUserApiService, this.serviceContainer.apiService, this.serviceContainer.eventCollectionService, this.serviceContainer.accountService);
        this.createCommand = new bw_CreateCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.apiService, this.serviceContainer.folderApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.organizationService, this.serviceContainer.accountService);
        this.editCommand = new bw_EditCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.apiService, this.serviceContainer.folderApiService, this.serviceContainer.accountService);
        this.generateCommand = new bw_GenerateCommand(this.serviceContainer.passwordGenerationService, this.serviceContainer.stateService);
        this.syncCommand = new bw_SyncCommand(this.serviceContainer.syncService);
        this.statusCommand = new bw_StatusCommand(this.serviceContainer.environmentService, this.serviceContainer.syncService, this.serviceContainer.accountService, this.serviceContainer.authService);
        this.deleteCommand = new bw_DeleteCommand(this.serviceContainer.cipherService, this.serviceContainer.folderService, this.serviceContainer.apiService, this.serviceContainer.folderApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.cipherAuthorizationService, this.serviceContainer.accountService);
        this.confirmCommand = new bw_ConfirmCommand(this.serviceContainer.apiService, this.serviceContainer.keyService, this.serviceContainer.encryptService, this.serviceContainer.organizationUserApiService);
        this.restoreCommand = new bw_RestoreCommand(this.serviceContainer.cipherService, this.serviceContainer.accountService);
        this.shareCommand = new bw_ShareCommand(this.serviceContainer.cipherService, this.serviceContainer.accountService);
        this.lockCommand = new bw_LockCommand(this.serviceContainer.vaultTimeoutService);
        this.unlockCommand = new bw_UnlockCommand(this.serviceContainer.accountService, this.serviceContainer.masterPasswordService, this.serviceContainer.keyService, this.serviceContainer.userVerificationService, this.serviceContainer.cryptoFunctionService, this.serviceContainer.logService, this.serviceContainer.keyConnectorService, this.serviceContainer.environmentService, this.serviceContainer.syncService, this.serviceContainer.organizationApiService, () => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () { return yield this.serviceContainer.logout(); }));
        this.sendCreateCommand = new bw_SendCreateCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.sendApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
        this.sendDeleteCommand = new bw_SendDeleteCommand(this.serviceContainer.sendService, this.serviceContainer.sendApiService);
        this.sendGetCommand = new bw_SendGetCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.searchService, this.serviceContainer.encryptService, this.serviceContainer.apiService);
        this.sendEditCommand = new bw_SendEditCommand(this.serviceContainer.sendService, this.sendGetCommand, this.serviceContainer.sendApiService, this.serviceContainer.billingAccountProfileStateService, this.serviceContainer.accountService);
        this.sendListCommand = new bw_SendListCommand(this.serviceContainer.sendService, this.serviceContainer.environmentService, this.serviceContainer.searchService);
        this.sendRemovePasswordCommand = new bw_SendRemovePasswordCommand(this.serviceContainer.sendService, this.serviceContainer.sendApiService, this.serviceContainer.environmentService);
    }
    configureRouter(router) {
        router.get("/generate", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            const response = yield this.generateCommand.run(ctx.request.query);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.get("/status", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            const response = yield this.statusCommand.run();
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.get("/list/object/:object", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            let response = null;
            if (ctx.params.object === "send") {
                response = yield this.sendListCommand.run(ctx.request.query);
            }
            else {
                response = yield this.listCommand.run(ctx.params.object, ctx.request.query);
            }
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.get("/send/list", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield this.sendListCommand.run(ctx.request.query);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/sync", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            const response = yield this.syncCommand.run(ctx.request.query);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/lock", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            const response = yield this.lockCommand.run();
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/unlock", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            // Do not allow guessing password location through serve command
            delete ctx.request.query.passwordFile;
            delete ctx.request.query.passwordEnv;
            const response = yield this.unlockCommand.run(ctx.request.body.password == null ? null : ctx.request.body.password, ctx.request.query);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/confirm/:object/:id", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield this.confirmCommand.run(ctx.params.object, ctx.params.id, ctx.request.query);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/restore/:object/:id", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield this.restoreCommand.run(ctx.params.object, ctx.params.id);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/move/:id/:organizationId", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield this.shareCommand.run(ctx.params.id, ctx.params.organizationId, ctx.request.body);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/attachment", bw_multer_namespaceObject().single("file"), (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield this.createCommand.run("attachment", ctx.request.body, ctx.request.query, {
                fileBuffer: ctx.request.file.buffer,
                fileName: ctx.request.file.originalname,
            });
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/send/:id/remove-password", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield this.sendRemovePasswordCommand.run(ctx.params.id);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/object/:object", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            let response = null;
            if (ctx.params.object === "send") {
                response = yield this.sendCreateCommand.run(ctx.request.body, ctx.request.query);
            }
            else {
                response = yield this.createCommand.run(ctx.params.object, ctx.request.body, ctx.request.query);
            }
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.put("/object/:object/:id", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            let response = null;
            if (ctx.params.object === "send") {
                ctx.request.body.id = ctx.params.id;
                response = yield this.sendEditCommand.run(ctx.request.body, ctx.request.query);
            }
            else {
                response = yield this.editCommand.run(ctx.params.object, ctx.params.id, ctx.request.body, ctx.request.query);
            }
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.get("/object/:object/:id", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            let response = null;
            if (ctx.params.object === "send") {
                response = yield this.sendGetCommand.run(ctx.params.id, null);
            }
            else {
                response = yield this.getCommand.run(ctx.params.object, ctx.params.id, ctx.request.query);
            }
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.delete("/object/:object/:id", (ctx, next) => bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            let response = null;
            if (ctx.params.object === "send") {
                response = yield this.sendDeleteCommand.run(ctx.params.id);
            }
            else {
                response = yield this.deleteCommand.run(ctx.params.object, ctx.params.id, ctx.request.query);
            }
            this.processResponse(ctx.response, response);
            yield next();
        }));
    }
    processResponse(res, commandResponse) {
        if (!commandResponse.success) {
            res.status = 400;
        }
        if (commandResponse.data instanceof bw_FileResponse) {
            res.body = commandResponse.data.data;
            res.attachment(commandResponse.data.fileName);
            res.set("Content-Type", "application/octet-stream");
            res.set("Content-Length", commandResponse.data.data.length.toString());
        }
        else {
            res.body = commandResponse;
        }
    }
    errorIfLocked(res) {
        return bw_oss_serve_configurator_awaiter(this, void 0, void 0, function* () {
            const authed = yield this.serviceContainer.stateService.getIsAuthenticated();
            if (!authed) {
                this.processResponse(res, bw_Response.error("You are not logged in."));
                return true;
            }
            if (yield this.serviceContainer.keyService.hasUserKey()) {
                return false;
            }
            this.processResponse(res, bw_Response.error("Vault is locked."));
            return true;
        });
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/approve-all.command.ts
var bw_approve_all_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_ApproveAllCommand {
    constructor(organizationAuthRequestService, organizationService, accountService) {
        this.organizationAuthRequestService = organizationAuthRequestService;
        this.organizationService = organizationService;
        this.accountService = accountService;
    }
    run(organizationId) {
        return bw_approve_all_command_awaiter(this, void 0, void 0, function* () {
            if (organizationId != null) {
                organizationId = organizationId.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(organizationId)) {
                return bw_Response.badRequest("`" + organizationId + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations.find((o) => o.id === organizationId))));
            if (!(organization === null || organization === void 0 ? void 0 : organization.canManageUsersPassword)) {
                return bw_Response.error("You do not have permission to approve pending device authorization requests.");
            }
            try {
                const pendingApprovals = yield this.organizationAuthRequestService.listPendingRequests(organizationId);
                if (pendingApprovals.length == 0) {
                    const res = new bw_MessageResponse("No pending device authorization requests to approve.", null);
                    return bw_Response.success(res);
                }
                yield this.organizationAuthRequestService.approvePendingRequests(organizationId, pendingApprovals);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    static create(serviceContainer) {
        return new bw_ApproveAllCommand(serviceContainer.organizationAuthRequestService, serviceContainer.organizationService, serviceContainer.accountService);
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/approve.command.ts
var bw_approve_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_ApproveCommand {
    constructor(organizationService, organizationAuthRequestService, accountService) {
        this.organizationService = organizationService;
        this.organizationAuthRequestService = organizationAuthRequestService;
        this.accountService = accountService;
    }
    run(organizationId, id) {
        return bw_approve_command_awaiter(this, void 0, void 0, function* () {
            if (organizationId != null) {
                organizationId = organizationId.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(organizationId)) {
                return bw_Response.badRequest("`" + organizationId + "` is not a GUID.");
            }
            if (id != null) {
                id = id.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations === null || organizations === void 0 ? void 0 : organizations.find((o) => o.id === organizationId))));
            if (!(organization === null || organization === void 0 ? void 0 : organization.canManageUsersPassword)) {
                return bw_Response.error("You do not have permission to approve pending device authorization requests.");
            }
            try {
                const pendingRequests = yield this.organizationAuthRequestService.listPendingRequests(organizationId);
                const request = pendingRequests.find((r) => r.id == id);
                if (request == null) {
                    return bw_Response.error("The request id is invalid.");
                }
                yield this.organizationAuthRequestService.approvePendingRequest(organizationId, request);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    static create(serviceContainer) {
        return new bw_ApproveCommand(serviceContainer.organizationService, serviceContainer.organizationAuthRequestService, serviceContainer.accountService);
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/deny-all.command.ts
var bw_deny_all_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_DenyAllCommand {
    constructor(organizationService, organizationAuthRequestService, accountService) {
        this.organizationService = organizationService;
        this.organizationAuthRequestService = organizationAuthRequestService;
        this.accountService = accountService;
    }
    run(organizationId) {
        return bw_deny_all_command_awaiter(this, void 0, void 0, function* () {
            if (organizationId != null) {
                organizationId = organizationId.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(organizationId)) {
                return bw_Response.badRequest("`" + organizationId + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations.find((o) => o.id === organizationId))));
            if (!(organization === null || organization === void 0 ? void 0 : organization.canManageUsersPassword)) {
                return bw_Response.error("You do not have permission to approve pending device authorization requests.");
            }
            try {
                const pendingRequests = yield this.organizationAuthRequestService.listPendingRequests(organizationId);
                if (pendingRequests.length == 0) {
                    const res = new bw_MessageResponse("No pending device authorization requests to deny.", null);
                    return bw_Response.success(res);
                }
                yield this.organizationAuthRequestService.denyPendingRequests(organizationId, ...pendingRequests.map((r) => r.id));
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    static create(serviceContainer) {
        return new bw_DenyAllCommand(serviceContainer.organizationService, serviceContainer.organizationAuthRequestService, serviceContainer.accountService);
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/deny.command.ts
var bw_deny_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_DenyCommand {
    constructor(organizationService, organizationAuthRequestService, accountServcie) {
        this.organizationService = organizationService;
        this.organizationAuthRequestService = organizationAuthRequestService;
        this.accountServcie = accountServcie;
    }
    run(organizationId, id) {
        return bw_deny_command_awaiter(this, void 0, void 0, function* () {
            if (organizationId != null) {
                organizationId = organizationId.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(organizationId)) {
                return bw_Response.badRequest("`" + organizationId + "` is not a GUID.");
            }
            if (id != null) {
                id = id.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(id)) {
                return bw_Response.badRequest("`" + id + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountServcie.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations.find((o) => o.id === organizationId))));
            if (!(organization === null || organization === void 0 ? void 0 : organization.canManageUsersPassword)) {
                return bw_Response.error("You do not have permission to approve pending device authorization requests.");
            }
            try {
                const pendingRequests = yield this.organizationAuthRequestService.listPendingRequests(organizationId);
                const request = pendingRequests.find((r) => r.id == id);
                if (request == null) {
                    return bw_Response.error("The request id is invalid.");
                }
                yield this.organizationAuthRequestService.denyPendingRequest(organizationId, id);
                return bw_Response.success();
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    static create(serviceContainer) {
        return new bw_DenyCommand(serviceContainer.organizationService, serviceContainer.organizationAuthRequestService, serviceContainer.accountService);
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/pending-auth-request.response.ts
class bw_PendingAuthRequestResponse {
    constructor(authRequest) {
        this.object = "auth-request";
        this.id = authRequest.id;
        this.userId = authRequest.userId;
        this.organizationUserId = authRequest.organizationUserId;
        this.email = authRequest.email;
        this.requestDeviceIdentifier = authRequest.requestDeviceIdentifier;
        this.requestDeviceType = authRequest.requestDeviceType;
        this.requestIpAddress = authRequest.requestIpAddress;
        this.creationDate = authRequest.creationDate;
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/list.command.ts
var bw_device_approval_list_command_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};






class bw_list_command_ListCommand {
    constructor(organizationAuthRequestService, organizationService, accountService) {
        this.organizationAuthRequestService = organizationAuthRequestService;
        this.organizationService = organizationService;
        this.accountService = accountService;
    }
    run(organizationId) {
        return bw_device_approval_list_command_awaiter(this, void 0, void 0, function* () {
            if (organizationId != null) {
                organizationId = organizationId.toLowerCase();
            }
            if (!bw_utils_Utils.isGuid(organizationId)) {
                return bw_Response.badRequest("`" + organizationId + "` is not a GUID.");
            }
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            if (!userId) {
                return bw_Response.badRequest("No user found.");
            }
            const organization = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((organizations) => organizations.find((o) => o.id === organizationId))));
            if (!(organization === null || organization === void 0 ? void 0 : organization.canManageUsersPassword)) {
                return bw_Response.error("You do not have permission to approve pending device authorization requests.");
            }
            try {
                const requests = yield this.organizationAuthRequestService.listPendingRequests(organizationId);
                const res = new bw_list_response_ListResponse(requests.map((r) => new bw_PendingAuthRequestResponse(r)));
                return bw_Response.success(res);
            }
            catch (e) {
                return bw_Response.error(e);
            }
        });
    }
    static create(serviceContainer) {
        return new bw_list_command_ListCommand(serviceContainer.organizationAuthRequestService, serviceContainer.organizationService, serviceContainer.accountService);
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/device-approval.program.ts
var bw_device_approval_program_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};







class bw_DeviceApprovalProgram extends bw_BaseProgram {
    constructor(serviceContainer) {
        super(serviceContainer);
        this.serviceContainer = serviceContainer;
    }
    register() {
        bw_external_commander_namespaceObject.program.addCommand(this.deviceApprovalCommand());
    }
    deviceApprovalCommand() {
        return new bw_external_commander_namespaceObject.Command("device-approval")
            .description("Manage device approval requests sent to organizations that use SSO with trusted devices.")
            .addCommand(this.listCommand())
            .addCommand(this.approveCommand())
            .addCommand(this.approveAllCommand())
            .addCommand(this.denyCommand())
            .addCommand(this.denyAllCommand());
    }
    listCommand() {
        return new bw_external_commander_namespaceObject.Command("list")
            .description("List all pending requests for an organization")
            .requiredOption("--organizationid <organizationid>", "The organization id (required)")
            .action((options) => bw_device_approval_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = bw_list_command_ListCommand.create(this.serviceContainer);
            const response = yield cmd.run(options.organizationid);
            this.processResponse(response);
        }));
    }
    approveCommand() {
        return new bw_external_commander_namespaceObject.Command("approve")
            .argument("<requestId>", "The id of the request to approve")
            .requiredOption("--organizationid <organizationid>", "The organization id (required)")
            .description("Approve a pending request")
            .action((id, options) => bw_device_approval_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = bw_ApproveCommand.create(this.serviceContainer);
            const response = yield cmd.run(options.organizationid, id);
            this.processResponse(response);
        }));
    }
    approveAllCommand() {
        return new bw_external_commander_namespaceObject.Command("approve-all")
            .description("Approve all pending requests for an organization")
            .requiredOption("--organizationid <organizationid>", "The organization id (required)")
            .action((options) => bw_device_approval_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = bw_ApproveAllCommand.create(this.serviceContainer);
            const response = yield cmd.run(options.organizationid);
            this.processResponse(response);
        }));
    }
    denyCommand() {
        return new bw_external_commander_namespaceObject.Command("deny")
            .argument("<requestId>", "The id of the request to deny")
            .requiredOption("--organizationid <organizationid>", "The organization id (required)")
            .description("Deny a pending request")
            .action((id, options) => bw_device_approval_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = bw_DenyCommand.create(this.serviceContainer);
            const response = yield cmd.run(options.organizationid, id);
            this.processResponse(response);
        }));
    }
    denyAllCommand() {
        return new bw_external_commander_namespaceObject.Command("deny-all")
            .description("Deny all pending requests for an organization")
            .requiredOption("--organizationid <organizationid>", "The organization id (required)")
            .action((options) => bw_device_approval_program_awaiter(this, void 0, void 0, function* () {
            yield this.exitIfLocked();
            const cmd = bw_DenyAllCommand.create(this.serviceContainer);
            const response = yield cmd.run(options.organizationid);
            this.processResponse(response);
        }));
    }
}

;// ../../bitwarden_license/bit-cli/src/admin-console/device-approval/index.ts







;// ../../bitwarden_license/bit-cli/src/bit-serve-configurator.ts
var bw_bit_serve_configurator_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_BitServeConfigurator extends bw_OssServeConfigurator {
    constructor(serviceContainer) {
        super(serviceContainer);
        this.serviceContainer = serviceContainer;
    }
    configureRouter(router) {
        // Register OSS endpoints
        super.configureRouter(router);
        // Register bit endpoints
        this.serveDeviceApprovals(router);
    }
    serveDeviceApprovals(router) {
        router.get("/device-approval/:organizationId", (ctx, next) => bw_bit_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield bw_list_command_ListCommand.create(this.serviceContainer).run(ctx.params.organizationId);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/device-approval/:organizationId/approve-all", (ctx, next) => bw_bit_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield bw_ApproveAllCommand.create(this.serviceContainer).run(ctx.params.organizationId);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/device-approval/:organizationId/approve/:requestId", (ctx, next) => bw_bit_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield bw_ApproveCommand.create(this.serviceContainer).run(ctx.params.organizationId, ctx.params.requestId);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/device-approval/:organizationId/deny-all", (ctx, next) => bw_bit_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield bw_DenyAllCommand.create(this.serviceContainer).run(ctx.params.organizationId);
            this.processResponse(ctx.response, response);
            yield next();
        }));
        router.post("/device-approval/:organizationId/deny/:requestId", (ctx, next) => bw_bit_serve_configurator_awaiter(this, void 0, void 0, function* () {
            if (yield this.errorIfLocked(ctx.response)) {
                yield next();
                return;
            }
            const response = yield bw_DenyCommand.create(this.serviceContainer).run(ctx.params.organizationId, ctx.params.requestId);
            this.processResponse(ctx.response, response);
            yield next();
        }));
    }
}

;// ../../bitwarden_license/bit-cli/src/register-bit-programs.ts
var bw_register_bit_programs_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

/**
 * All Bitwarden-licensed programs should be registered here.
 * @example
 * const myProgram = new myProgram(serviceContainer);
 * myProgram.register();
 * @param serviceContainer A class that instantiates services and makes them available for dependency injection
 */
function bw_registerBitPrograms(serviceContainer) {
    return bw_register_bit_programs_awaiter(this, void 0, void 0, function* () {
        new bw_DeviceApprovalProgram(serviceContainer).register();
    });
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/pending-organization-auth-request.response.ts

class bw_PendingOrganizationAuthRequestResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.userId = this.getResponseProperty("UserId");
        this.organizationUserId = this.getResponseProperty("OrganizationUserId");
        this.email = this.getResponseProperty("Email");
        this.publicKey = this.getResponseProperty("PublicKey");
        this.requestDeviceIdentifier = this.getResponseProperty("RequestDeviceIdentifier");
        this.requestDeviceType = this.getResponseProperty("RequestDeviceType");
        this.requestIpAddress = this.getResponseProperty("RequestIpAddress");
        this.requestCountryName = this.getResponseProperty("RequestCountryName");
        this.creationDate = this.getResponseProperty("CreationDate");
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/organization-auth-request-update.request.ts
class bw_OrganizationAuthRequestUpdateRequest {
    constructor(id, approved, key) {
        this.id = id;
        this.approved = approved;
        this.key = key;
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/organization-auth-request.service.ts
var bw_organization_auth_request_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_OrganizationAuthRequestService {
    constructor(organizationAuthRequestApiService, keyService, encryptService, organizationUserApiService) {
        this.organizationAuthRequestApiService = organizationAuthRequestApiService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.organizationUserApiService = organizationUserApiService;
    }
    listPendingRequests(organizationId) {
        return bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
            return yield this.organizationAuthRequestApiService.listPendingRequests(organizationId);
        });
    }
    denyPendingRequests(organizationId, ...requestIds) {
        return bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
            yield this.organizationAuthRequestApiService.denyPendingRequests(organizationId, ...requestIds);
        });
    }
    approvePendingRequests(organizationId, authRequests) {
        return bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const organizationUserIds = authRequests.map((r) => r.organizationUserId);
            const details = yield this.organizationUserApiService.getManyOrganizationUserAccountRecoveryDetails(organizationId, organizationUserIds);
            if (details == null ||
                details.data.length == 0 ||
                details.data.some((d) => d.resetPasswordKey == null)) {
                throw new Error("All users must be enrolled in account recovery (password reset) in order for the requests to be approved.");
            }
            const requestsToApprove = yield Promise.all(authRequests.map((r) => bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
                const detail = details.data.find((d) => d.organizationUserId === r.organizationUserId);
                const encryptedKey = yield this.getEncryptedUserKey(organizationId, r.publicKey, detail);
                return new bw_OrganizationAuthRequestUpdateRequest(r.id, true, encryptedKey.encryptedString);
            })));
            yield this.organizationAuthRequestApiService.bulkUpdatePendingRequests(organizationId, requestsToApprove);
        });
    }
    approvePendingRequest(organizationId, authRequest) {
        return bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const details = yield this.organizationUserApiService.getOrganizationUserResetPasswordDetails(organizationId, authRequest.organizationUserId);
            if (details == null || details.resetPasswordKey == null) {
                throw new Error("The user must be enrolled in account recovery (password reset) in order for the request to be approved.");
            }
            const encryptedKey = yield this.getEncryptedUserKey(organizationId, authRequest.publicKey, details);
            yield this.organizationAuthRequestApiService.approvePendingRequest(organizationId, authRequest.id, encryptedKey);
        });
    }
    denyPendingRequest(organizationId, requestId) {
        return bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
            yield this.organizationAuthRequestApiService.denyPendingRequest(organizationId, requestId);
        });
    }
    /**
     * Creates a copy of the user key that has been encrypted with the provided device's public key.
     * @param organizationId
     * @param devicePublicKey
     * @param resetPasswordDetails
     * @private
     */
    getEncryptedUserKey(organizationId, devicePublicKey, resetPasswordDetails) {
        return bw_organization_auth_request_service_awaiter(this, void 0, void 0, function* () {
            const encryptedUserKey = resetPasswordDetails.resetPasswordKey;
            const encryptedOrgPrivateKey = resetPasswordDetails.encryptedPrivateKey;
            const devicePubKey = bw_utils_Utils.fromB64ToArray(devicePublicKey);
            // Decrypt Organization's encrypted Private Key with org key
            const orgSymKey = yield this.keyService.getOrgKey(organizationId);
            const decOrgPrivateKey = yield this.encryptService.decryptToBytes(new bw_enc_string_EncString(encryptedOrgPrivateKey), orgSymKey);
            // Decrypt user key with decrypted org private key
            const decValue = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(encryptedUserKey), decOrgPrivateKey);
            const userKey = new bw_SymmetricCryptoKey(decValue);
            // Re-encrypt user Key with the Device Public Key
            return yield this.encryptService.rsaEncrypt(userKey.key, devicePubKey);
        });
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/admin-auth-request-update.request.ts
class bw_AdminAuthRequestUpdateRequest {
    /**
     *
     * @param requestApproved - Whether the request was approved/denied. If true, the key must be provided.
     * @param encryptedUserKey The user key that has been encrypted with a device public key if the request was approved.
     */
    constructor(requestApproved, encryptedUserKey) {
        this.requestApproved = requestApproved;
        this.encryptedUserKey = encryptedUserKey;
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/bulk-deny-auth-requests.request.ts
class bw_BulkDenyAuthRequestsRequest {
    constructor(authRequestIds) {
        this.ids = authRequestIds;
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/pending-auth-request.view.ts
class bw_PendingAuthRequestView {
    static fromResponse(response) {
        const view = Object.assign(new bw_PendingAuthRequestView(), response);
        view.creationDate = new Date(response.creationDate);
        return view;
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/organization-auth-request-api.service.ts
var bw_organization_auth_request_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_OrganizationAuthRequestApiService {
    constructor(apiService) {
        this.apiService = apiService;
    }
    listPendingRequests(organizationId) {
        return bw_organization_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", `/organizations/${organizationId}/auth-requests`, null, true, true);
            const listResponse = new bw_ListResponse(r, bw_PendingOrganizationAuthRequestResponse);
            return listResponse.data.map((ar) => bw_PendingAuthRequestView.fromResponse(ar));
        });
    }
    denyPendingRequests(organizationId, ...requestIds) {
        return bw_organization_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", `/organizations/${organizationId}/auth-requests/deny`, new bw_BulkDenyAuthRequestsRequest(requestIds), true, false);
        });
    }
    bulkUpdatePendingRequests(organizationId, items) {
        return bw_organization_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", `/organizations/${organizationId}/auth-requests`, items, true, false);
        });
    }
    approvePendingRequest(organizationId, requestId, encryptedKey) {
        return bw_organization_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", `/organizations/${organizationId}/auth-requests/${requestId}`, new bw_AdminAuthRequestUpdateRequest(true, encryptedKey.encryptedString), true, false);
        });
    }
    denyPendingRequest(organizationId, requestId) {
        return bw_organization_auth_request_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", `/organizations/${organizationId}/auth-requests/${requestId}`, new bw_AdminAuthRequestUpdateRequest(false), true, false);
        });
    }
}

;// ../../bitwarden_license/bit-common/src/admin-console/auth-requests/index.ts





;// external "jsdom"
const bw_external_jsdom_namespaceObject = require("jsdom");
;// ../../libs/common/src/billing/enums/payment-method-type.enum.ts
var bw_PaymentMethodType;
(function (PaymentMethodType) {
    PaymentMethodType[PaymentMethodType["Card"] = 0] = "Card";
    PaymentMethodType[PaymentMethodType["BankAccount"] = 1] = "BankAccount";
    PaymentMethodType[PaymentMethodType["PayPal"] = 2] = "PayPal";
    PaymentMethodType[PaymentMethodType["BitPay"] = 3] = "BitPay";
    PaymentMethodType[PaymentMethodType["Credit"] = 4] = "Credit";
    PaymentMethodType[PaymentMethodType["WireTransfer"] = 5] = "WireTransfer";
    PaymentMethodType[PaymentMethodType["Check"] = 8] = "Check";
})(bw_PaymentMethodType || (bw_PaymentMethodType = {}));

;// ../../libs/common/src/billing/enums/plan-sponsorship-type.enum.ts
var bw_PlanSponsorshipType;
(function (PlanSponsorshipType) {
    PlanSponsorshipType[PlanSponsorshipType["FamiliesForEnterprise"] = 0] = "FamiliesForEnterprise";
})(bw_PlanSponsorshipType || (bw_PlanSponsorshipType = {}));

;// ../../libs/common/src/billing/enums/plan-type.enum.ts
var bw_PlanType;
(function (PlanType) {
    PlanType[PlanType["Free"] = 0] = "Free";
    PlanType[PlanType["FamiliesAnnually2019"] = 1] = "FamiliesAnnually2019";
    PlanType[PlanType["TeamsMonthly2019"] = 2] = "TeamsMonthly2019";
    PlanType[PlanType["TeamsAnnually2019"] = 3] = "TeamsAnnually2019";
    PlanType[PlanType["EnterpriseMonthly2019"] = 4] = "EnterpriseMonthly2019";
    PlanType[PlanType["EnterpriseAnnually2019"] = 5] = "EnterpriseAnnually2019";
    PlanType[PlanType["Custom"] = 6] = "Custom";
    PlanType[PlanType["FamiliesAnnually"] = 7] = "FamiliesAnnually";
    PlanType[PlanType["TeamsMonthly2020"] = 8] = "TeamsMonthly2020";
    PlanType[PlanType["TeamsAnnually2020"] = 9] = "TeamsAnnually2020";
    PlanType[PlanType["EnterpriseMonthly2020"] = 10] = "EnterpriseMonthly2020";
    PlanType[PlanType["EnterpriseAnnually2020"] = 11] = "EnterpriseAnnually2020";
    PlanType[PlanType["TeamsMonthly2023"] = 12] = "TeamsMonthly2023";
    PlanType[PlanType["TeamsAnnually2023"] = 13] = "TeamsAnnually2023";
    PlanType[PlanType["EnterpriseMonthly2023"] = 14] = "EnterpriseMonthly2023";
    PlanType[PlanType["EnterpriseAnnually2023"] = 15] = "EnterpriseAnnually2023";
    PlanType[PlanType["TeamsStarter2023"] = 16] = "TeamsStarter2023";
    PlanType[PlanType["TeamsMonthly"] = 17] = "TeamsMonthly";
    PlanType[PlanType["TeamsAnnually"] = 18] = "TeamsAnnually";
    PlanType[PlanType["EnterpriseMonthly"] = 19] = "EnterpriseMonthly";
    PlanType[PlanType["EnterpriseAnnually"] = 20] = "EnterpriseAnnually";
    PlanType[PlanType["TeamsStarter"] = 21] = "TeamsStarter";
})(bw_PlanType || (bw_PlanType = {}));

;// ../../libs/common/src/billing/enums/transaction-type.enum.ts
var bw_TransactionType;
(function (TransactionType) {
    TransactionType[TransactionType["Charge"] = 0] = "Charge";
    TransactionType[TransactionType["Credit"] = 1] = "Credit";
    TransactionType[TransactionType["PromotionalCredit"] = 2] = "PromotionalCredit";
    TransactionType[TransactionType["ReferralCredit"] = 3] = "ReferralCredit";
    TransactionType[TransactionType["Refund"] = 4] = "Refund";
})(bw_TransactionType || (bw_TransactionType = {}));

;// ../../libs/common/src/billing/enums/bitwarden-product-type.enum.ts
var bw_BitwardenProductType;
(function (BitwardenProductType) {
    BitwardenProductType[BitwardenProductType["PasswordManager"] = 0] = "PasswordManager";
    BitwardenProductType[BitwardenProductType["SecretsManager"] = 1] = "SecretsManager";
})(bw_BitwardenProductType || (bw_BitwardenProductType = {}));

;// ../../libs/common/src/billing/enums/product-tier-type.enum.ts
var bw_ProductTierType;
(function (ProductTierType) {
    ProductTierType[ProductTierType["Free"] = 0] = "Free";
    ProductTierType[ProductTierType["Families"] = 1] = "Families";
    ProductTierType[ProductTierType["Teams"] = 2] = "Teams";
    ProductTierType[ProductTierType["Enterprise"] = 3] = "Enterprise";
    ProductTierType[ProductTierType["TeamsStarter"] = 4] = "TeamsStarter";
})(bw_ProductTierType || (bw_ProductTierType = {}));
function bw_isNotSelfUpgradable(productType) {
    return (productType !== bw_ProductTierType.Free &&
        productType !== bw_ProductTierType.TeamsStarter &&
        productType !== bw_ProductTierType.Families);
}

;// ../../libs/common/src/billing/enums/product-type.enum.ts
var bw_ProductType;
(function (ProductType) {
    ProductType[ProductType["PasswordManager"] = 0] = "PasswordManager";
    ProductType[ProductType["SecretsManager"] = 1] = "SecretsManager";
})(bw_ProductType || (bw_ProductType = {}));

;// ../../libs/common/src/billing/enums/plan-interval.enum.ts
var bw_PlanInterval;
(function (PlanInterval) {
    PlanInterval[PlanInterval["Monthly"] = 0] = "Monthly";
    PlanInterval[PlanInterval["Annually"] = 1] = "Annually";
})(bw_PlanInterval || (bw_PlanInterval = {}));

;// ../../libs/common/src/billing/enums/index.ts









;// ../../libs/common/src/admin-console/models/domain/organization.ts


class bw_Organization {
    constructor(obj) {
        if (obj == null) {
            return;
        }
        this.id = obj.id;
        this.name = obj.name;
        this.status = obj.status;
        this.type = obj.type;
        this.enabled = obj.enabled;
        this.usePolicies = obj.usePolicies;
        this.useGroups = obj.useGroups;
        this.useDirectory = obj.useDirectory;
        this.useEvents = obj.useEvents;
        this.useTotp = obj.useTotp;
        this.use2fa = obj.use2fa;
        this.useApi = obj.useApi;
        this.useSso = obj.useSso;
        this.useKeyConnector = obj.useKeyConnector;
        this.useScim = obj.useScim;
        this.useCustomPermissions = obj.useCustomPermissions;
        this.useResetPassword = obj.useResetPassword;
        this.useSecretsManager = obj.useSecretsManager;
        this.usePasswordManager = obj.usePasswordManager;
        this.useActivateAutofillPolicy = obj.useActivateAutofillPolicy;
        this.selfHost = obj.selfHost;
        this.usersGetPremium = obj.usersGetPremium;
        this.seats = obj.seats;
        this.maxCollections = obj.maxCollections;
        this.maxStorageGb = obj.maxStorageGb;
        this.ssoBound = obj.ssoBound;
        this.identifier = obj.identifier;
        this.permissions = obj.permissions;
        this.resetPasswordEnrolled = obj.resetPasswordEnrolled;
        this.userId = obj.userId;
        this.organizationUserId = obj.organizationUserId;
        this.hasPublicAndPrivateKeys = obj.hasPublicAndPrivateKeys;
        this.providerId = obj.providerId;
        this.providerName = obj.providerName;
        this.providerType = obj.providerType;
        this.isProviderUser = obj.isProviderUser;
        this.isMember = obj.isMember;
        this.familySponsorshipFriendlyName = obj.familySponsorshipFriendlyName;
        this.familySponsorshipAvailable = obj.familySponsorshipAvailable;
        this.productTierType = obj.productTierType;
        this.keyConnectorEnabled = obj.keyConnectorEnabled;
        this.keyConnectorUrl = obj.keyConnectorUrl;
        this.familySponsorshipLastSyncDate = obj.familySponsorshipLastSyncDate;
        this.familySponsorshipValidUntil = obj.familySponsorshipValidUntil;
        this.familySponsorshipToDelete = obj.familySponsorshipToDelete;
        this.accessSecretsManager = obj.accessSecretsManager;
        this.limitCollectionCreation = obj.limitCollectionCreation;
        this.limitCollectionDeletion = obj.limitCollectionDeletion;
        this.limitItemDeletion = obj.limitItemDeletion;
        this.allowAdminAccessToAllCollectionItems = obj.allowAdminAccessToAllCollectionItems;
        this.userIsManagedByOrganization = obj.userIsManagedByOrganization;
        this.useRiskInsights = obj.useRiskInsights;
    }
    get canAccess() {
        if (this.isOwner) {
            return true;
        }
        return this.enabled && this.status === bw_OrganizationUserStatusType.Confirmed;
    }
    /**
     * Whether a user has Admin permissions or greater
     */
    get isAdmin() {
        return this.type === bw_OrganizationUserType.Admin || this.isOwner;
    }
    /**
     * Whether a user has Owner permissions (including ProviderUsers)
     */
    get isOwner() {
        return this.type === bw_OrganizationUserType.Owner || this.isProviderUser;
    }
    get canAccessEventLogs() {
        return (this.isAdmin || this.permissions.accessEventLogs) && this.useEvents;
    }
    /**
     * Returns true if the user can access the Import page in the Admin Console.
     * Note: this does not affect user access to the Import page in Password Manager, which can also be used to import
     * into organization collections.
     */
    get canAccessImport() {
        return (this.isProviderUser ||
            this.type === bw_OrganizationUserType.Owner ||
            this.type === bw_OrganizationUserType.Admin ||
            this.permissions.accessImportExport);
    }
    get canAccessExport() {
        return (this.isMember &&
            (this.type === bw_OrganizationUserType.Owner ||
                this.type === bw_OrganizationUserType.Admin ||
                this.permissions.accessImportExport));
    }
    get canAccessReports() {
        return this.isAdmin || this.permissions.accessReports;
    }
    get canCreateNewCollections() {
        return !this.limitCollectionCreation || this.isAdmin || this.permissions.createNewCollections;
    }
    get canEditAnyCollection() {
        // The allowAdminAccessToAllCollectionItems flag can restrict admins
        // Providers and custom users with canEditAnyCollection are not affected by allowAdminAccessToAllCollectionItems flag
        return (this.isProviderUser ||
            (this.type === bw_OrganizationUserType.Custom && this.permissions.editAnyCollection) ||
            (this.allowAdminAccessToAllCollectionItems && this.isAdmin));
    }
    get canEditUnmanagedCollections() {
        // Any admin or custom user with editAnyCollection permission can edit unmanaged collections
        return this.isAdmin || this.permissions.editAnyCollection;
    }
    get canEditUnassignedCiphers() {
        return (this.type === bw_OrganizationUserType.Admin ||
            this.type === bw_OrganizationUserType.Owner ||
            this.permissions.editAnyCollection);
    }
    get canEditAllCiphers() {
        // The allowAdminAccessToAllCollectionItems flag can restrict admins
        // Custom users with canEditAnyCollection are not affected by allowAdminAccessToAllCollectionItems flag
        return ((this.type === bw_OrganizationUserType.Custom && this.permissions.editAnyCollection) ||
            (this.allowAdminAccessToAllCollectionItems &&
                (this.type === bw_OrganizationUserType.Admin || this.type === bw_OrganizationUserType.Owner)));
    }
    /**
     * @returns True if the user can delete any collection
     */
    get canDeleteAnyCollection() {
        // Providers and Users with DeleteAnyCollection permission can always delete collections
        if (this.isProviderUser || this.permissions.deleteAnyCollection) {
            return true;
        }
        // If AllowAdminAccessToAllCollectionItems is true, Owners and Admins can delete any collection, regardless of LimitCollectionDeletion setting
        // Using explicit type checks because provider users are handled above and this mimics the server's permission checks closely
        if (this.allowAdminAccessToAllCollectionItems) {
            return this.type == bw_OrganizationUserType.Owner || this.type == bw_OrganizationUserType.Admin;
        }
        return false;
    }
    /**
     * Whether the user can view all collection information, such as collection name and access.
     * This does not indicate that the user can view items inside any collection - for that, see {@link canEditAllCiphers}
     */
    get canViewAllCollections() {
        // Admins can always see all collections even if collection management settings prevent them from editing them or seeing items
        return (this.isAdmin || this.permissions.editAnyCollection || this.permissions.deleteAnyCollection);
    }
    get canManageGroups() {
        return (this.isAdmin || this.permissions.manageGroups) && this.useGroups;
    }
    get canManageSso() {
        return (this.isAdmin || this.permissions.manageSso) && this.useSso;
    }
    get canManageDomainVerification() {
        return (this.isAdmin || this.permissions.manageSso) && this.useSso;
    }
    get canManageScim() {
        return (this.isAdmin || this.permissions.manageScim) && this.useScim;
    }
    get canManagePolicies() {
        return (this.isAdmin || this.permissions.managePolicies) && this.usePolicies;
    }
    get canManageUsers() {
        return this.isAdmin || this.permissions.manageUsers;
    }
    get canManageUsersPassword() {
        return this.isAdmin || this.permissions.manageResetPassword;
    }
    get canManageDeviceApprovals() {
        return (this.isAdmin || this.permissions.manageResetPassword) && this.useSso;
    }
    get isExemptFromPolicies() {
        return this.canManagePolicies;
    }
    get canViewSubscription() {
        if (this.canEditSubscription) {
            return true;
        }
        return this.hasBillableProvider ? this.isProviderUser : this.isOwner;
    }
    get canEditSubscription() {
        return this.hasProvider ? this.isProviderUser : this.isOwner;
    }
    get canEditPaymentMethods() {
        return this.canEditSubscription;
    }
    get canViewBillingHistory() {
        return this.canEditSubscription;
    }
    get hasProvider() {
        return this.providerId != null || this.providerName != null;
    }
    get hasBillableProvider() {
        return (this.hasProvider &&
            (this.providerType === bw_ProviderType.Msp ||
                this.providerType === bw_ProviderType.MultiOrganizationEnterprise));
    }
    get hasReseller() {
        return this.hasProvider && this.providerType === bw_ProviderType.Reseller;
    }
    get canAccessSecretsManager() {
        return this.useSecretsManager && this.accessSecretsManager;
    }
    get isFreeOrg() {
        // return true if organization needs to be upgraded from a free org
        return !this.useTotp;
    }
    get canManageSponsorships() {
        return this.familySponsorshipAvailable || this.familySponsorshipFriendlyName !== null;
    }
    static fromJSON(json) {
        if (json == null) {
            return null;
        }
        return Object.assign(new bw_Organization(), json, {
            familySponsorshipLastSyncDate: new Date(json.familySponsorshipLastSyncDate),
            familySponsorshipValidUntil: new Date(json.familySponsorshipValidUntil),
        });
    }
    get canAccessIntegrations() {
        return ((this.productTierType === bw_ProductTierType.Teams ||
            this.productTierType === bw_ProductTierType.Enterprise) &&
            (this.isAdmin ||
                this.permissions.manageUsers ||
                this.permissions.manageGroups ||
                this.permissions.accessEventLogs));
    }
}

;// ../../libs/common/src/admin-console/models/data/organization.data.ts
class bw_OrganizationData {
    constructor(response, options) {
        if (response == null) {
            return;
        }
        this.id = response.id;
        this.name = response.name;
        this.status = response.status;
        this.type = response.type;
        this.enabled = response.enabled;
        this.usePolicies = response.usePolicies;
        this.useGroups = response.useGroups;
        this.useDirectory = response.useDirectory;
        this.useEvents = response.useEvents;
        this.useTotp = response.useTotp;
        this.use2fa = response.use2fa;
        this.useApi = response.useApi;
        this.useSso = response.useSso;
        this.useKeyConnector = response.useKeyConnector;
        this.useScim = response.useScim;
        this.useCustomPermissions = response.useCustomPermissions;
        this.useResetPassword = response.useResetPassword;
        this.useSecretsManager = response.useSecretsManager;
        this.usePasswordManager = response.usePasswordManager;
        this.useActivateAutofillPolicy = response.useActivateAutofillPolicy;
        this.selfHost = response.selfHost;
        this.usersGetPremium = response.usersGetPremium;
        this.seats = response.seats;
        this.maxCollections = response.maxCollections;
        this.maxStorageGb = response.maxStorageGb;
        this.ssoBound = response.ssoBound;
        this.identifier = response.identifier;
        this.permissions = response.permissions;
        this.resetPasswordEnrolled = response.resetPasswordEnrolled;
        this.userId = response.userId;
        this.organizationUserId = response.organizationUserId;
        this.hasPublicAndPrivateKeys = response.hasPublicAndPrivateKeys;
        this.providerId = response.providerId;
        this.providerName = response.providerName;
        this.providerType = response.providerType;
        this.familySponsorshipFriendlyName = response.familySponsorshipFriendlyName;
        this.familySponsorshipAvailable = response.familySponsorshipAvailable;
        this.productTierType = response.productTierType;
        this.keyConnectorEnabled = response.keyConnectorEnabled;
        this.keyConnectorUrl = response.keyConnectorUrl;
        this.familySponsorshipLastSyncDate = response.familySponsorshipLastSyncDate;
        this.familySponsorshipValidUntil = response.familySponsorshipValidUntil;
        this.familySponsorshipToDelete = response.familySponsorshipToDelete;
        this.accessSecretsManager = response.accessSecretsManager;
        this.limitCollectionCreation = response.limitCollectionCreation;
        this.limitCollectionDeletion = response.limitCollectionDeletion;
        this.limitItemDeletion = response.limitItemDeletion;
        this.allowAdminAccessToAllCollectionItems = response.allowAdminAccessToAllCollectionItems;
        this.userIsManagedByOrganization = response.userIsManagedByOrganization;
        this.useRiskInsights = response.useRiskInsights;
        this.isMember = options.isMember;
        this.isProviderUser = options.isProviderUser;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_OrganizationData(), obj, {
            familySponsorshipLastSyncDate: obj.familySponsorshipLastSyncDate != null
                ? new Date(obj.familySponsorshipLastSyncDate)
                : obj.familySponsorshipLastSyncDate,
            familySponsorshipValidUntil: obj.familySponsorshipValidUntil != null
                ? new Date(obj.familySponsorshipValidUntil)
                : obj.familySponsorshipValidUntil,
        });
    }
}

;// ../../libs/common/src/admin-console/services/organization/organization.state.ts


/**
 * The `KeyDefinition` for accessing organization lists in application state.
 * @todo Ideally this wouldn't require a `fromJSON()` call, but `OrganizationData`
 * has some properties that contain functions. This should probably get
 * cleaned up.
 */
const bw_ORGANIZATIONS = bw_UserKeyDefinition.record(bw_ORGANIZATIONS_DISK, "organizations", {
    deserializer: (obj) => bw_OrganizationData.fromJSON(obj),
    clearOn: ["logout"],
});

;// ../../libs/common/src/admin-console/services/organization/default-organization.service.ts
var bw_default_organization_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



/**
 * Filter out organizations from an observable that __do not__ offer a
 * families-for-enterprise sponsorship to members.
 * @returns a function that can be used in `Observable<Organization[]>` pipes,
 * like `organizationService.organizations$`
 */
function bw_mapToExcludeOrganizationsWithoutFamilySponsorshipSupport() {
    return (0,bw_external_rxjs_namespaceObject.map)((orgs) => orgs.filter((o) => o.canManageSponsorships));
}
/**
 * Filter out organizations from an observable that the organization user
 * __is not__ a direct member of. This will exclude organizations only
 * accessible as a provider.
 * @returns a function that can be used in `Observable<Organization[]>` pipes,
 * like `organizationService.organizations$`
 */
function bw_mapToExcludeProviderOrganizations() {
    return (0,bw_external_rxjs_namespaceObject.map)((orgs) => orgs.filter((o) => o.isMember));
}
/**
 * Map an observable stream of organizations down to a boolean indicating
 * if any organizations exist (`orgs.length > 0`).
 * @returns a function that can be used in `Observable<Organization[]>` pipes,
 * like `organizationService.organizations$`
 */
function bw_mapToBooleanHasAnyOrganizations() {
    return (0,bw_external_rxjs_namespaceObject.map)((orgs) => orgs.length > 0);
}
class bw_DefaultOrganizationService {
    memberOrganizations$(userId) {
        return this.organizations$(userId).pipe(bw_mapToExcludeProviderOrganizations());
    }
    constructor(stateProvider) {
        this.stateProvider = stateProvider;
    }
    canManageSponsorships$(userId) {
        return this.organizations$(userId).pipe(bw_mapToExcludeOrganizationsWithoutFamilySponsorshipSupport(), bw_mapToBooleanHasAnyOrganizations());
    }
    familySponsorshipAvailable$(userId) {
        return this.organizations$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((orgs) => orgs.some((o) => o.familySponsorshipAvailable)));
    }
    hasOrganizations(userId) {
        return this.organizations$(userId).pipe(bw_mapToBooleanHasAnyOrganizations());
    }
    upsert(organization, userId) {
        return bw_default_organization_service_awaiter(this, void 0, void 0, function* () {
            yield this.organizationState(userId).update((existingOrganizations) => {
                const organizations = existingOrganizations !== null && existingOrganizations !== void 0 ? existingOrganizations : {};
                organizations[organization.id] = organization;
                return organizations;
            });
        });
    }
    replace(organizations, userId) {
        return bw_default_organization_service_awaiter(this, void 0, void 0, function* () {
            yield this.organizationState(userId).update(() => organizations);
        });
    }
    organizations$(userId) {
        return this.organizationState(userId).state$.pipe(this.mapOrganizationRecordToArray());
    }
    organizationState(userId) {
        return this.stateProvider.getUser(userId, bw_ORGANIZATIONS);
    }
    /**
     * Accepts a record of `OrganizationData`, which is how we store the
     * organization list as a JSON object on disk, to an array of
     * `Organization`, which is how the data is published to callers of the
     * service.
     * @returns a function that can be used to pipe organization data from
     * stored state to an exposed object easily consumable by others.
     */
    mapOrganizationRecordToArray() {
        return (0,bw_external_rxjs_namespaceObject.map)((orgs) => { var _a; return (_a = Object.values(orgs !== null && orgs !== void 0 ? orgs : {})) === null || _a === void 0 ? void 0 : _a.map((o) => new bw_Organization(o)); });
    }
}

;// ../../libs/common/src/auth/models/response/api-key.response.ts

class bw_ApiKeyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.apiKey = this.getResponseProperty("ApiKey");
        this.revisionDate = new Date(this.getResponseProperty("RevisionDate"));
    }
}

;// ../../libs/common/src/auth/enums/sso.ts
var bw_SsoType;
(function (SsoType) {
    SsoType[SsoType["None"] = 0] = "None";
    SsoType[SsoType["OpenIdConnect"] = 1] = "OpenIdConnect";
    SsoType[SsoType["Saml2"] = 2] = "Saml2";
})(bw_SsoType || (bw_SsoType = {}));
var bw_MemberDecryptionType;
(function (MemberDecryptionType) {
    MemberDecryptionType[MemberDecryptionType["MasterPassword"] = 0] = "MasterPassword";
    MemberDecryptionType[MemberDecryptionType["KeyConnector"] = 1] = "KeyConnector";
    MemberDecryptionType[MemberDecryptionType["TrustedDeviceEncryption"] = 2] = "TrustedDeviceEncryption";
})(bw_MemberDecryptionType || (bw_MemberDecryptionType = {}));
var bw_OpenIdConnectRedirectBehavior;
(function (OpenIdConnectRedirectBehavior) {
    OpenIdConnectRedirectBehavior[OpenIdConnectRedirectBehavior["RedirectGet"] = 0] = "RedirectGet";
    OpenIdConnectRedirectBehavior[OpenIdConnectRedirectBehavior["FormPost"] = 1] = "FormPost";
})(bw_OpenIdConnectRedirectBehavior || (bw_OpenIdConnectRedirectBehavior = {}));
var bw_Saml2BindingType;
(function (Saml2BindingType) {
    Saml2BindingType[Saml2BindingType["HttpRedirect"] = 1] = "HttpRedirect";
    Saml2BindingType[Saml2BindingType["HttpPost"] = 2] = "HttpPost";
})(bw_Saml2BindingType || (bw_Saml2BindingType = {}));
var bw_Saml2NameIdFormat;
(function (Saml2NameIdFormat) {
    Saml2NameIdFormat[Saml2NameIdFormat["NotConfigured"] = 0] = "NotConfigured";
    Saml2NameIdFormat[Saml2NameIdFormat["Unspecified"] = 1] = "Unspecified";
    Saml2NameIdFormat[Saml2NameIdFormat["EmailAddress"] = 2] = "EmailAddress";
    Saml2NameIdFormat[Saml2NameIdFormat["X509SubjectName"] = 3] = "X509SubjectName";
    Saml2NameIdFormat[Saml2NameIdFormat["WindowsDomainQualifiedName"] = 4] = "WindowsDomainQualifiedName";
    Saml2NameIdFormat[Saml2NameIdFormat["KerberosPrincipalName"] = 5] = "KerberosPrincipalName";
    Saml2NameIdFormat[Saml2NameIdFormat["EntityIdentifier"] = 6] = "EntityIdentifier";
    Saml2NameIdFormat[Saml2NameIdFormat["Persistent"] = 7] = "Persistent";
    Saml2NameIdFormat[Saml2NameIdFormat["Transient"] = 8] = "Transient";
})(bw_Saml2NameIdFormat || (bw_Saml2NameIdFormat = {}));
var bw_Saml2SigningBehavior;
(function (Saml2SigningBehavior) {
    Saml2SigningBehavior[Saml2SigningBehavior["IfIdpWantAuthnRequestsSigned"] = 0] = "IfIdpWantAuthnRequestsSigned";
    Saml2SigningBehavior[Saml2SigningBehavior["Always"] = 1] = "Always";
    Saml2SigningBehavior[Saml2SigningBehavior["Never"] = 3] = "Never";
})(bw_Saml2SigningBehavior || (bw_Saml2SigningBehavior = {}));

;// ../../libs/common/src/auth/models/api/sso-config.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_SsoConfigApi extends bw_BaseResponse {
    static fromView(view, api = new bw_SsoConfigApi()) {
        api.configType = view.configType;
        api.memberDecryptionType = view.memberDecryptionType;
        api.keyConnectorUrl = view.keyConnectorUrl;
        if (api.configType === bw_SsoType.OpenIdConnect) {
            api.authority = view.openId.authority;
            api.clientId = view.openId.clientId;
            api.clientSecret = view.openId.clientSecret;
            api.metadataAddress = view.openId.metadataAddress;
            api.redirectBehavior = view.openId.redirectBehavior;
            api.getClaimsFromUserInfoEndpoint = view.openId.getClaimsFromUserInfoEndpoint;
            api.additionalScopes = view.openId.additionalScopes;
            api.additionalUserIdClaimTypes = view.openId.additionalUserIdClaimTypes;
            api.additionalEmailClaimTypes = view.openId.additionalEmailClaimTypes;
            api.additionalNameClaimTypes = view.openId.additionalNameClaimTypes;
            api.acrValues = view.openId.acrValues;
            api.expectedReturnAcrValue = view.openId.expectedReturnAcrValue;
        }
        else if (api.configType === bw_SsoType.Saml2) {
            api.spUniqueEntityId = view.saml.spUniqueEntityId;
            api.spNameIdFormat = view.saml.spNameIdFormat;
            api.spOutboundSigningAlgorithm = view.saml.spOutboundSigningAlgorithm;
            api.spSigningBehavior = view.saml.spSigningBehavior;
            api.spMinIncomingSigningAlgorithm = view.saml.spMinIncomingSigningAlgorithm;
            api.spWantAssertionsSigned = view.saml.spWantAssertionsSigned;
            api.spValidateCertificates = view.saml.spValidateCertificates;
            api.idpEntityId = view.saml.idpEntityId;
            api.idpBindingType = view.saml.idpBindingType;
            api.idpSingleSignOnServiceUrl = view.saml.idpSingleSignOnServiceUrl;
            api.idpSingleLogoutServiceUrl = view.saml.idpSingleLogoutServiceUrl;
            api.idpX509PublicCert = view.saml.idpX509PublicCert;
            api.idpOutboundSigningAlgorithm = view.saml.idpOutboundSigningAlgorithm;
            api.idpAllowUnsolicitedAuthnResponse = view.saml.idpAllowUnsolicitedAuthnResponse;
            api.idpWantAuthnRequestsSigned = view.saml.idpWantAuthnRequestsSigned;
            // Value is inverted in the api model (disable instead of allow)
            api.idpDisableOutboundLogoutRequests = !view.saml.idpAllowOutboundLogoutRequests;
        }
        return api;
    }
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.configType = this.getResponseProperty("ConfigType");
        this.memberDecryptionType = this.getResponseProperty("MemberDecryptionType");
        this.keyConnectorUrl = this.getResponseProperty("KeyConnectorUrl");
        this.authority = this.getResponseProperty("Authority");
        this.clientId = this.getResponseProperty("ClientId");
        this.clientSecret = this.getResponseProperty("ClientSecret");
        this.metadataAddress = this.getResponseProperty("MetadataAddress");
        this.redirectBehavior = this.getResponseProperty("RedirectBehavior");
        this.getClaimsFromUserInfoEndpoint = this.getResponseProperty("GetClaimsFromUserInfoEndpoint");
        this.additionalScopes = this.getResponseProperty("AdditionalScopes");
        this.additionalUserIdClaimTypes = this.getResponseProperty("AdditionalUserIdClaimTypes");
        this.additionalEmailClaimTypes = this.getResponseProperty("AdditionalEmailClaimTypes");
        this.additionalNameClaimTypes = this.getResponseProperty("AdditionalNameClaimTypes");
        this.acrValues = this.getResponseProperty("AcrValues");
        this.expectedReturnAcrValue = this.getResponseProperty("ExpectedReturnAcrValue");
        this.spUniqueEntityId = this.getResponseProperty("SpUniqueEntityId");
        this.spNameIdFormat = this.getResponseProperty("SpNameIdFormat");
        this.spOutboundSigningAlgorithm = this.getResponseProperty("SpOutboundSigningAlgorithm");
        this.spSigningBehavior = this.getResponseProperty("SpSigningBehavior");
        this.spMinIncomingSigningAlgorithm = this.getResponseProperty("SpMinIncomingSigningAlgorithm");
        this.spWantAssertionsSigned = this.getResponseProperty("SpWantAssertionsSigned");
        this.spValidateCertificates = this.getResponseProperty("SpValidateCertificates");
        this.idpEntityId = this.getResponseProperty("IdpEntityId");
        this.idpBindingType = this.getResponseProperty("IdpBindingType");
        this.idpSingleSignOnServiceUrl = this.getResponseProperty("IdpSingleSignOnServiceUrl");
        this.idpSingleLogoutServiceUrl = this.getResponseProperty("IdpSingleLogoutServiceUrl");
        this.idpX509PublicCert = this.getResponseProperty("IdpX509PublicCert");
        this.idpOutboundSigningAlgorithm = this.getResponseProperty("IdpOutboundSigningAlgorithm");
        this.idpAllowUnsolicitedAuthnResponse = this.getResponseProperty("IdpAllowUnsolicitedAuthnResponse");
        this.idpDisableOutboundLogoutRequests = this.getResponseProperty("IdpDisableOutboundLogoutRequests");
        this.idpWantAuthnRequestsSigned = this.getResponseProperty("IdpWantAuthnRequestsSigned");
    }
}

;// ../../libs/common/src/auth/models/response/organization-sso.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_OrganizationSsoResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        this.identifier = this.getResponseProperty("Identifier");
        this.data =
            this.getResponseProperty("Data") != null
                ? new bw_SsoConfigApi(this.getResponseProperty("Data"))
                : null;
        this.urls = new bw_SsoUrls(this.getResponseProperty("Urls"));
    }
}
class bw_SsoUrls extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.callbackPath = this.getResponseProperty("CallbackPath");
        this.signedOutCallbackPath = this.getResponseProperty("SignedOutCallbackPath");
        this.spEntityId = this.getResponseProperty("SpEntityId");
        this.spEntityIdStatic = this.getResponseProperty("SpEntityIdStatic");
        this.spMetadataUrl = this.getResponseProperty("SpMetadataUrl");
        this.spAcsUrl = this.getResponseProperty("SpAcsUrl");
    }
}

;// ../../libs/common/src/billing/models/response/billing.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_BillingResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.balance = this.getResponseProperty("Balance");
        const paymentSource = this.getResponseProperty("PaymentSource");
        this.paymentSource = paymentSource == null ? null : new bw_BillingSourceResponse(paymentSource);
    }
}
class bw_BillingSourceResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.type = this.getResponseProperty("Type");
        this.cardBrand = this.getResponseProperty("CardBrand");
        this.description = this.getResponseProperty("Description");
        this.needsVerification = this.getResponseProperty("NeedsVerification");
    }
}
class bw_BillingInvoiceResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.url = this.getResponseProperty("Url");
        this.pdfUrl = this.getResponseProperty("PdfUrl");
        this.number = this.getResponseProperty("Number");
        this.paid = this.getResponseProperty("Paid");
        this.date = this.getResponseProperty("Date");
        this.amount = this.getResponseProperty("Amount");
    }
}
class bw_BillingTransactionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.createdDate = this.getResponseProperty("CreatedDate");
        this.amount = this.getResponseProperty("Amount");
        this.refunded = this.getResponseProperty("Refunded");
        this.partiallyRefunded = this.getResponseProperty("PartiallyRefunded");
        this.refundedAmount = this.getResponseProperty("RefundedAmount");
        this.type = this.getResponseProperty("Type");
        this.paymentMethodType = this.getResponseProperty("PaymentMethodType");
        this.details = this.getResponseProperty("Details");
    }
}

;// ../../libs/common/src/billing/models/response/billing-history.response.ts


class bw_BillingHistoryResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.invoices = [];
        this.transactions = [];
        const transactions = this.getResponseProperty("Transactions");
        const invoices = this.getResponseProperty("Invoices");
        if (transactions != null) {
            this.transactions = transactions.map((t) => new bw_BillingTransactionResponse(t));
        }
        if (invoices != null) {
            this.invoices = invoices.map((i) => new bw_BillingInvoiceResponse(i));
        }
    }
    get hasNoHistory() {
        return this.invoices.length == 0 && this.transactions.length == 0;
    }
}

;// ../../libs/common/src/billing/models/response/plan.response.ts

class bw_PlanResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.type = this.getResponseProperty("Type");
        this.productTier = this.getResponseProperty("ProductTier");
        this.name = this.getResponseProperty("Name");
        this.isAnnual = this.getResponseProperty("IsAnnual");
        this.nameLocalizationKey = this.getResponseProperty("NameLocalizationKey");
        this.descriptionLocalizationKey = this.getResponseProperty("DescriptionLocalizationKey");
        this.canBeUsedByBusiness = this.getResponseProperty("CanBeUsedByBusiness");
        this.trialPeriodDays = this.getResponseProperty("TrialPeriodDays");
        this.hasSelfHost = this.getResponseProperty("HasSelfHost");
        this.hasPolicies = this.getResponseProperty("HasPolicies");
        this.hasGroups = this.getResponseProperty("HasGroups");
        this.hasDirectory = this.getResponseProperty("HasDirectory");
        this.hasEvents = this.getResponseProperty("HasEvents");
        this.hasTotp = this.getResponseProperty("HasTotp");
        this.has2fa = this.getResponseProperty("Has2fa");
        this.hasApi = this.getResponseProperty("HasApi");
        this.hasSso = this.getResponseProperty("HasSso");
        this.hasResetPassword = this.getResponseProperty("HasResetPassword");
        this.usersGetPremium = this.getResponseProperty("UsersGetPremium");
        this.upgradeSortOrder = this.getResponseProperty("UpgradeSortOrder");
        this.displaySortOrder = this.getResponseProperty("DisplaySortOrder");
        this.legacyYear = this.getResponseProperty("LegacyYear");
        this.disabled = this.getResponseProperty("Disabled");
        const passwordManager = this.getResponseProperty("PasswordManager");
        const secretsManager = this.getResponseProperty("SecretsManager");
        this.PasswordManager =
            passwordManager == null ? null : new bw_PasswordManagerPlanFeaturesResponse(passwordManager);
        this.SecretsManager =
            secretsManager == null ? null : new bw_SecretsManagerPlanFeaturesResponse(secretsManager);
    }
}
class bw_SecretsManagerPlanFeaturesResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.stripeSeatPlanId = this.getResponseProperty("StripeSeatPlanId");
        this.baseSeats = this.getResponseProperty("BaseSeats");
        this.basePrice = this.getResponseProperty("BasePrice");
        this.seatPrice = this.getResponseProperty("SeatPrice");
        this.hasAdditionalSeatsOption = this.getResponseProperty("HasAdditionalSeatsOption");
        this.maxAdditionalSeats = this.getResponseProperty("MaxAdditionalSeats");
        this.maxSeats = this.getResponseProperty("MaxSeats");
        this.stripeServiceAccountPlanId = this.getResponseProperty("StripeServiceAccountPlanId");
        this.additionalPricePerServiceAccount = this.getResponseProperty("AdditionalPricePerServiceAccount");
        this.baseServiceAccount = this.getResponseProperty("BaseServiceAccount");
        this.maxServiceAccount = this.getResponseProperty("MaxServiceAccount");
        this.hasAdditionalServiceAccountOption = this.getResponseProperty("HasAdditionalServiceAccountOption");
        this.maxAdditionalServiceAccounts = this.getResponseProperty("MaxAdditionalServiceAccounts");
        this.maxProjects = this.getResponseProperty("MaxProjects");
    }
}
class bw_PasswordManagerPlanFeaturesResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.stripePlanId = this.getResponseProperty("StripePlanId");
        this.stripeSeatPlanId = this.getResponseProperty("StripeSeatPlanId");
        this.stripeProviderPortalSeatPlanId = this.getResponseProperty("StripeProviderPortalSeatPlanId");
        this.stripeStoragePlanId = this.getResponseProperty("StripeStoragePlanId");
        this.stripePremiumAccessPlanId = this.getResponseProperty("StripePremiumAccessPlanId");
        this.basePrice = this.getResponseProperty("BasePrice");
        this.seatPrice = this.getResponseProperty("SeatPrice");
        this.providerPortalSeatPrice = this.getResponseProperty("ProviderPortalSeatPrice");
        this.baseSeats = this.getResponseProperty("BaseSeats");
        this.maxAdditionalSeats = this.getResponseProperty("MaxAdditionalSeats");
        this.premiumAccessOptionPrice = this.getResponseProperty("PremiumAccessOptionPrice");
        this.maxSeats = this.getResponseProperty("MaxSeats");
        this.additionalStoragePricePerGb = this.getResponseProperty("AdditionalStoragePricePerGb");
        this.hasAdditionalSeatsOption = this.getResponseProperty("HasAdditionalSeatsOption");
        this.baseStorageGb = this.getResponseProperty("BaseStorageGb");
        this.maxCollections = this.getResponseProperty("MaxCollections");
        this.hasAdditionalStorageOption = this.getResponseProperty("HasAdditionalStorageOption");
        this.maxAdditionalStorage = this.getResponseProperty("MaxAdditionalStorage");
        this.hasPremiumAccessOption = this.getResponseProperty("HasPremiumAccessOption");
    }
}

;// ../../libs/common/src/admin-console/models/response/organization.response.ts


class bw_organization_response_OrganizationResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.name = this.getResponseProperty("Name");
        this.businessName = this.getResponseProperty("BusinessName");
        this.businessAddress1 = this.getResponseProperty("BusinessAddress1");
        this.businessAddress2 = this.getResponseProperty("BusinessAddress2");
        this.businessAddress3 = this.getResponseProperty("BusinessAddress3");
        this.businessCountry = this.getResponseProperty("BusinessCountry");
        this.businessTaxNumber = this.getResponseProperty("BusinessTaxNumber");
        this.billingEmail = this.getResponseProperty("BillingEmail");
        const plan = this.getResponseProperty("Plan");
        this.plan = plan == null ? null : new bw_PlanResponse(plan);
        this.planType = this.getResponseProperty("PlanType");
        this.seats = this.getResponseProperty("Seats");
        this.maxAutoscaleSeats = this.getResponseProperty("MaxAutoscaleSeats");
        this.maxCollections = this.getResponseProperty("MaxCollections");
        this.maxStorageGb = this.getResponseProperty("MaxStorageGb");
        this.useGroups = this.getResponseProperty("UseGroups");
        this.useDirectory = this.getResponseProperty("UseDirectory");
        this.useEvents = this.getResponseProperty("UseEvents");
        this.useTotp = this.getResponseProperty("UseTotp");
        this.use2fa = this.getResponseProperty("Use2fa");
        this.useApi = this.getResponseProperty("UseApi");
        this.useResetPassword = this.getResponseProperty("UseResetPassword");
        this.useSecretsManager = this.getResponseProperty("UseSecretsManager");
        this.hasPublicAndPrivateKeys = this.getResponseProperty("HasPublicAndPrivateKeys");
        this.usePasswordManager = this.getResponseProperty("UsePasswordManager");
        this.smSeats = this.getResponseProperty("SmSeats");
        this.smServiceAccounts = this.getResponseProperty("SmServiceAccounts");
        this.maxAutoscaleSmSeats = this.getResponseProperty("MaxAutoscaleSmSeats");
        this.maxAutoscaleSmServiceAccounts = this.getResponseProperty("MaxAutoscaleSmServiceAccounts");
        this.limitCollectionCreation = this.getResponseProperty("LimitCollectionCreation");
        this.limitCollectionDeletion = this.getResponseProperty("LimitCollectionDeletion");
        this.limitItemDeletion = this.getResponseProperty("LimitItemDeletion");
        this.allowAdminAccessToAllCollectionItems = this.getResponseProperty("AllowAdminAccessToAllCollectionItems");
        this.useRiskInsights = this.getResponseProperty("UseRiskInsights");
    }
}

;// ../../libs/common/src/billing/models/response/subscription.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SubscriptionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.storageName = this.getResponseProperty("StorageName");
        this.storageGb = this.getResponseProperty("StorageGb");
        this.maxStorageGb = this.getResponseProperty("MaxStorageGb");
        this.license = this.getResponseProperty("License");
        this.expiration = this.getResponseProperty("Expiration");
        const subscription = this.getResponseProperty("Subscription");
        const upcomingInvoice = this.getResponseProperty("UpcomingInvoice");
        this.subscription = subscription == null ? null : new bw_BillingSubscriptionResponse(subscription);
        this.upcomingInvoice =
            upcomingInvoice == null
                ? null
                : new bw_BillingSubscriptionUpcomingInvoiceResponse(upcomingInvoice);
    }
}
class bw_BillingSubscriptionResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.items = [];
        this.trialStartDate = this.getResponseProperty("TrialStartDate");
        this.trialEndDate = this.getResponseProperty("TrialEndDate");
        this.periodStartDate = this.getResponseProperty("PeriodStartDate");
        this.periodEndDate = this.getResponseProperty("PeriodEndDate");
        this.cancelledDate = this.getResponseProperty("CancelledDate");
        this.cancelAtEndDate = this.getResponseProperty("CancelAtEndDate");
        this.status = this.getResponseProperty("Status");
        this.cancelled = this.getResponseProperty("Cancelled");
        const items = this.getResponseProperty("Items");
        if (items != null) {
            this.items = items.map((i) => new bw_BillingSubscriptionItemResponse(i));
        }
        this.collectionMethod = this.getResponseProperty("CollectionMethod");
        this.suspensionDate = this.getResponseProperty("SuspensionDate");
        this.unpaidPeriodEndDate = this.getResponseProperty("unpaidPeriodEndDate");
        this.gracePeriod = this.getResponseProperty("GracePeriod");
    }
}
class bw_BillingSubscriptionItemResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.productId = this.getResponseProperty("ProductId");
        this.name = this.getResponseProperty("Name");
        this.amount = this.getResponseProperty("Amount");
        this.quantity = this.getResponseProperty("Quantity");
        this.interval = this.getResponseProperty("Interval");
        this.sponsoredSubscriptionItem = this.getResponseProperty("SponsoredSubscriptionItem");
        this.addonSubscriptionItem = this.getResponseProperty("AddonSubscriptionItem");
    }
}
class bw_BillingSubscriptionUpcomingInvoiceResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.date = this.getResponseProperty("Date");
        this.amount = this.getResponseProperty("Amount");
    }
}

;// ../../libs/common/src/billing/models/response/organization-subscription.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_OrganizationSubscriptionResponse extends bw_organization_response_OrganizationResponse {
    constructor(response) {
        super(response);
        this.storageName = this.getResponseProperty("StorageName");
        this.storageGb = this.getResponseProperty("StorageGb");
        const subscription = this.getResponseProperty("Subscription");
        this.subscription = subscription == null ? null : new bw_BillingSubscriptionResponse(subscription);
        const upcomingInvoice = this.getResponseProperty("UpcomingInvoice");
        this.upcomingInvoice =
            upcomingInvoice == null
                ? null
                : new bw_BillingSubscriptionUpcomingInvoiceResponse(upcomingInvoice);
        const customerDiscount = this.getResponseProperty("CustomerDiscount");
        this.customerDiscount =
            customerDiscount == null ? null : new bw_BillingCustomerDiscount(customerDiscount);
        this.expiration = this.getResponseProperty("Expiration");
        this.expirationWithoutGracePeriod = this.getResponseProperty("ExpirationWithoutGracePeriod");
    }
}
class bw_BillingCustomerDiscount extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.active = this.getResponseProperty("Active");
        this.percentOff = this.getResponseProperty("PercentOff");
        this.appliesTo = this.getResponseProperty("AppliesTo");
    }
}

;// ../../libs/common/src/admin-console/models/response/profile-organization.response.ts


class bw_ProfileOrganizationResponse extends bw_BaseResponse {
    constructor(response) {
        var _a, _b, _c, _d;
        super(response);
        this.id = this.getResponseProperty("Id");
        this.name = this.getResponseProperty("Name");
        this.usePolicies = this.getResponseProperty("UsePolicies");
        this.useGroups = this.getResponseProperty("UseGroups");
        this.useDirectory = this.getResponseProperty("UseDirectory");
        this.useEvents = this.getResponseProperty("UseEvents");
        this.useTotp = this.getResponseProperty("UseTotp");
        this.use2fa = this.getResponseProperty("Use2fa");
        this.useApi = this.getResponseProperty("UseApi");
        this.useSso = this.getResponseProperty("UseSso");
        this.useKeyConnector = (_a = this.getResponseProperty("UseKeyConnector")) !== null && _a !== void 0 ? _a : false;
        this.useScim = (_b = this.getResponseProperty("UseScim")) !== null && _b !== void 0 ? _b : false;
        this.useCustomPermissions = (_c = this.getResponseProperty("UseCustomPermissions")) !== null && _c !== void 0 ? _c : false;
        this.useResetPassword = this.getResponseProperty("UseResetPassword");
        this.useSecretsManager = this.getResponseProperty("UseSecretsManager");
        this.usePasswordManager = this.getResponseProperty("UsePasswordManager");
        this.useActivateAutofillPolicy = this.getResponseProperty("UseActivateAutofillPolicy");
        this.selfHost = this.getResponseProperty("SelfHost");
        this.usersGetPremium = this.getResponseProperty("UsersGetPremium");
        this.seats = this.getResponseProperty("Seats");
        this.maxCollections = this.getResponseProperty("MaxCollections");
        this.maxStorageGb = this.getResponseProperty("MaxStorageGb");
        this.key = this.getResponseProperty("Key");
        this.hasPublicAndPrivateKeys = this.getResponseProperty("HasPublicAndPrivateKeys");
        this.status = this.getResponseProperty("Status");
        this.type = this.getResponseProperty("Type");
        this.enabled = this.getResponseProperty("Enabled");
        this.ssoBound = this.getResponseProperty("SsoBound");
        this.identifier = this.getResponseProperty("Identifier");
        this.permissions = new bw_PermissionsApi(this.getResponseProperty("permissions"));
        this.resetPasswordEnrolled = this.getResponseProperty("ResetPasswordEnrolled");
        this.userId = this.getResponseProperty("UserId");
        this.organizationUserId = this.getResponseProperty("OrganizationUserId");
        this.providerId = this.getResponseProperty("ProviderId");
        this.providerName = this.getResponseProperty("ProviderName");
        this.providerType = this.getResponseProperty("ProviderType");
        this.familySponsorshipFriendlyName = this.getResponseProperty("FamilySponsorshipFriendlyName");
        this.familySponsorshipAvailable = this.getResponseProperty("FamilySponsorshipAvailable");
        this.productTierType = this.getResponseProperty("ProductTierType");
        this.keyConnectorEnabled = (_d = this.getResponseProperty("KeyConnectorEnabled")) !== null && _d !== void 0 ? _d : false;
        this.keyConnectorUrl = this.getResponseProperty("KeyConnectorUrl");
        const familySponsorshipLastSyncDateString = this.getResponseProperty("FamilySponsorshipLastSyncDate");
        if (familySponsorshipLastSyncDateString) {
            this.familySponsorshipLastSyncDate = new Date(familySponsorshipLastSyncDateString);
        }
        const familySponsorshipValidUntilString = this.getResponseProperty("FamilySponsorshipValidUntil");
        if (familySponsorshipValidUntilString) {
            this.familySponsorshipValidUntil = new Date(familySponsorshipValidUntilString);
        }
        this.familySponsorshipToDelete = this.getResponseProperty("FamilySponsorshipToDelete");
        this.accessSecretsManager = this.getResponseProperty("AccessSecretsManager");
        this.limitCollectionCreation = this.getResponseProperty("LimitCollectionCreation");
        this.limitCollectionDeletion = this.getResponseProperty("LimitCollectionDeletion");
        this.limitItemDeletion = this.getResponseProperty("LimitItemDeletion");
        this.allowAdminAccessToAllCollectionItems = this.getResponseProperty("AllowAdminAccessToAllCollectionItems");
        this.userIsManagedByOrganization = this.getResponseProperty("UserIsManagedByOrganization");
        this.useRiskInsights = this.getResponseProperty("UseRiskInsights");
    }
}

;// ../../libs/common/src/admin-console/models/response/profile-provider-organization.response.ts

class bw_ProfileProviderOrganizationResponse extends bw_ProfileOrganizationResponse {
    constructor(response) {
        super(response);
        this.keyConnectorEnabled = false;
    }
}

;// ../../libs/common/src/admin-console/models/response/profile-provider.response.ts


class bw_ProfileProviderResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.name = this.getResponseProperty("Name");
        this.key = this.getResponseProperty("Key");
        this.status = this.getResponseProperty("Status");
        this.type = this.getResponseProperty("Type");
        this.enabled = this.getResponseProperty("Enabled");
        this.permissions = new bw_PermissionsApi(this.getResponseProperty("permissions"));
        this.userId = this.getResponseProperty("UserId");
        this.useEvents = this.getResponseProperty("UseEvents");
        this.providerStatus = this.getResponseProperty("ProviderStatus");
    }
}

;// ../../libs/common/src/models/response/profile.response.ts




class bw_ProfileResponse extends bw_BaseResponse {
    constructor(response) {
        var _a, _b, _c;
        super(response);
        this.organizations = [];
        this.providers = [];
        this.providerOrganizations = [];
        this.id = this.getResponseProperty("Id");
        this.name = this.getResponseProperty("Name");
        this.email = this.getResponseProperty("Email");
        this.emailVerified = this.getResponseProperty("EmailVerified");
        this.premiumPersonally = this.getResponseProperty("Premium");
        this.premiumFromOrganization = this.getResponseProperty("PremiumFromOrganization");
        this.culture = this.getResponseProperty("Culture");
        this.twoFactorEnabled = this.getResponseProperty("TwoFactorEnabled");
        this.key = this.getResponseProperty("Key");
        this.avatarColor = this.getResponseProperty("AvatarColor");
        this.creationDate = this.getResponseProperty("CreationDate");
        this.privateKey = this.getResponseProperty("PrivateKey");
        this.securityStamp = this.getResponseProperty("SecurityStamp");
        this.forcePasswordReset = (_a = this.getResponseProperty("ForcePasswordReset")) !== null && _a !== void 0 ? _a : false;
        this.usesKeyConnector = (_b = this.getResponseProperty("UsesKeyConnector")) !== null && _b !== void 0 ? _b : false;
        this.verifyDevices = (_c = this.getResponseProperty("VerifyDevices")) !== null && _c !== void 0 ? _c : true;
        const organizations = this.getResponseProperty("Organizations");
        if (organizations != null) {
            this.organizations = organizations.map((o) => new bw_ProfileOrganizationResponse(o));
        }
        const providers = this.getResponseProperty("Providers");
        if (providers != null) {
            this.providers = providers.map((o) => new bw_ProfileProviderResponse(o));
        }
        const providerOrganizations = this.getResponseProperty("ProviderOrganizations");
        if (providerOrganizations != null) {
            this.providerOrganizations = providerOrganizations.map((o) => new bw_ProfileProviderOrganizationResponse(o));
        }
    }
}

;// ../../libs/common/src/billing/models/response/payment.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_PaymentResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        const userProfile = this.getResponseProperty("UserProfile");
        if (userProfile != null) {
            this.userProfile = new bw_ProfileResponse(userProfile);
        }
        this.paymentIntentClientSecret = this.getResponseProperty("PaymentIntentClientSecret");
        this.success = this.getResponseProperty("Success");
    }
}

;// ../../libs/common/src/billing/models/response/tax-info.response.ts

class bw_TaxInfoResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.taxId = this.getResponseProperty("TaxIdNumber");
        if (!this.taxId) {
            this.taxId = this.getResponseProperty("TaxId");
        }
        this.taxIdType = this.getResponseProperty("TaxIdType");
        this.line1 = this.getResponseProperty("Line1");
        this.line2 = this.getResponseProperty("Line2");
        this.city = this.getResponseProperty("City");
        this.state = this.getResponseProperty("State");
        this.postalCode = this.getResponseProperty("PostalCode");
        this.country = this.getResponseProperty("Country");
    }
}

;// ../../libs/common/src/admin-console/models/response/organization-api-key-information.response.ts

class bw_OrganizationApiKeyInformationResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.keyType = this.getResponseProperty("KeyType");
    }
}

;// ../../libs/common/src/admin-console/models/response/organization-auto-enroll-status.response.ts

class bw_OrganizationAutoEnrollStatusResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.resetPasswordEnabled = this.getResponseProperty("ResetPasswordEnabled");
    }
}

;// ../../libs/common/src/models/response/keys.response.ts

class bw_KeysResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.privateKey = this.getResponseProperty("PrivateKey");
        this.publicKey = this.getResponseProperty("PublicKey");
    }
}

;// ../../libs/common/src/admin-console/models/response/organization-keys.response.ts

class bw_OrganizationKeysResponse extends bw_KeysResponse {
    constructor(response) {
        super(response);
    }
}

;// ../../libs/common/src/admin-console/services/organization/organization-api.service.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
var bw_organization_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};













class bw_OrganizationApiService {
    constructor(apiService, syncService) {
        this.apiService = apiService;
        this.syncService = syncService;
    }
    get(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id, null, true, true);
            return new bw_organization_response_OrganizationResponse(r);
        });
    }
    getBilling(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id + "/billing", null, true, true);
            return new bw_BillingResponse(r);
        });
    }
    getBillingHistory(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id + "/billing/history", null, true, true);
            return new bw_BillingHistoryResponse(r);
        });
    }
    getSubscription(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id + "/subscription", null, true, true);
            return new bw_OrganizationSubscriptionResponse(r);
        });
    }
    getLicense(id, installationId) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            return this.apiService.send("GET", "/organizations/" + id + "/license?installationId=" + installationId, null, true, true);
        });
    }
    getAutoEnrollStatus(identifier) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + identifier + "/auto-enroll-status", null, true, true);
            return new bw_OrganizationAutoEnrollStatusResponse(r);
        });
    }
    create(request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations", request, true, true);
            // Forcing a sync will notify organization service that they need to repull
            yield this.syncService.fullSync(true);
            return new bw_organization_response_OrganizationResponse(r);
        });
    }
    createWithoutPayment(request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/create-without-payment", request, true, true);
            // Forcing a sync will notify organization service that they need to repull
            yield this.syncService.fullSync(true);
            return new bw_organization_response_OrganizationResponse(r);
        });
    }
    createLicense(data) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/licenses/self-hosted", data, true, true);
            return new bw_organization_response_OrganizationResponse(r);
        });
    }
    save(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/organizations/" + id, request, true, true);
            const data = new bw_organization_response_OrganizationResponse(r);
            yield this.syncService.fullSync(true);
            return data;
        });
    }
    updatePayment(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            return this.apiService.send("POST", "/organizations/" + id + "/payment", request, true, false);
        });
    }
    upgrade(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/upgrade", request, true, true);
            return new bw_PaymentResponse(r);
        });
    }
    updatePasswordManagerSeats(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/subscription", request, true, true);
            return new bw_ProfileOrganizationResponse(r);
        });
    }
    updateSecretsManagerSubscription(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/sm-subscription", request, true, true);
            return new bw_ProfileOrganizationResponse(r);
        });
    }
    updateSeats(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/seat", request, true, true);
            return new bw_PaymentResponse(r);
        });
    }
    updateStorage(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/storage", request, true, true);
            return new bw_PaymentResponse(r);
        });
    }
    verifyBank(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", "/organizations/" + id + "/verify-bank", request, true, false);
        });
    }
    reinstate(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            return this.apiService.send("POST", "/organizations/" + id + "/reinstate", null, true, false);
        });
    }
    leave(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", "/organizations/" + id + "/leave", null, true, false);
            yield this.syncService.fullSync(true);
        });
    }
    delete(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("DELETE", "/organizations/" + id, request, true, false);
            yield this.syncService.fullSync(true);
        });
    }
    deleteUsingToken(organizationId, request) {
        return this.apiService.send("POST", "/organizations/" + organizationId + "/delete-recover-token", request, false, false);
    }
    updateLicense(id, data) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", "/organizations/licenses/self-hosted/" + id, data, true, false);
        });
    }
    importDirectory(organizationId, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            return this.apiService.send("POST", "/organizations/" + organizationId + "/import", request, true, false);
        });
    }
    getOrCreateApiKey(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/api-key", request, true, true);
            return new bw_ApiKeyResponse(r);
        });
    }
    getApiKeyInformation(id_1) {
        return bw_organization_api_service_awaiter(this, arguments, void 0, function* (id, organizationApiKeyType = null) {
            const uri = organizationApiKeyType === null
                ? "/organizations/" + id + "/api-key-information"
                : "/organizations/" + id + "/api-key-information/" + organizationApiKeyType;
            const r = yield this.apiService.send("GET", uri, null, true, true);
            return new bw_ListResponse(r, bw_OrganizationApiKeyInformationResponse);
        });
    }
    rotateApiKey(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/rotate-api-key", request, true, true);
            return new bw_ApiKeyResponse(r);
        });
    }
    getTaxInfo(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id + "/tax", null, true, true);
            return new bw_TaxInfoResponse(r);
        });
    }
    updateTaxInfo(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            // Can't broadcast anything because the response doesn't have content
            return this.apiService.send("PUT", "/organizations/" + id + "/tax", request, true, false);
        });
    }
    getKeys(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id + "/keys", null, true, true);
            return new bw_OrganizationKeysResponse(r);
        });
    }
    updateKeys(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/keys", request, true, true);
            // Not broadcasting anything because data on this response doesn't correspond to `Organization`
            return new bw_OrganizationKeysResponse(r);
        });
    }
    getSso(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + id + "/sso", null, true, true);
            return new bw_OrganizationSsoResponse(r);
        });
    }
    updateSso(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/sso", request, true, true);
            // Not broadcasting anything because data on this response doesn't correspond to `Organization`
            return new bw_OrganizationSsoResponse(r);
        });
    }
    selfHostedSyncLicense(id) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", "/organizations/licenses/self-hosted/" + id + "/sync/", null, true, false);
        });
    }
    subscribeToSecretsManager(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/organizations/" + id + "/subscribe-secrets-manager", request, true, true);
            return new bw_ProfileOrganizationResponse(r);
        });
    }
    updateCollectionManagement(id, request) {
        return bw_organization_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/organizations/" + id + "/collection-management", request, true, true);
            const data = new bw_organization_response_OrganizationResponse(r);
            yield this.syncService.fullSync(true);
            return data;
        });
    }
}

;// ../../libs/common/src/admin-console/models/data/policy.data.ts
class bw_PolicyData {
    constructor(response) {
        if (response == null) {
            return;
        }
        this.id = response.id;
        this.organizationId = response.organizationId;
        this.type = response.type;
        this.data = response.data;
        this.enabled = response.enabled;
    }
    static fromPolicy(policy) {
        return Object.assign(new bw_PolicyData(), policy);
    }
}

;// ../../libs/common/src/admin-console/models/domain/policy.ts


class bw_Policy extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.id = obj.id;
        this.organizationId = obj.organizationId;
        this.type = obj.type;
        this.data = obj.data;
        this.enabled = obj.enabled;
    }
    static fromResponse(response) {
        return new bw_Policy(new bw_PolicyData(response));
    }
    static fromListResponse(response) {
        var _a, _b;
        return (_b = (_a = response.data) === null || _a === void 0 ? void 0 : _a.map((d) => bw_Policy.fromResponse(d))) !== null && _b !== void 0 ? _b : undefined;
    }
}

;// ../../libs/common/src/admin-console/models/response/policy.response.ts

class bw_PolicyResponse extends bw_BaseResponse {
    constructor(response) {
        var _a;
        super(response);
        this.id = this.getResponseProperty("Id");
        this.organizationId = this.getResponseProperty("OrganizationId");
        this.type = this.getResponseProperty("Type");
        this.data = this.getResponseProperty("Data");
        this.enabled = this.getResponseProperty("Enabled");
        this.canToggleState = (_a = this.getResponseProperty("CanToggleState")) !== null && _a !== void 0 ? _a : true;
    }
}

;// ../../libs/common/src/admin-console/services/policy/policy-api.service.ts
var bw_policy_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};








class bw_PolicyApiService {
    constructor(policyService, apiService) {
        this.policyService = policyService;
        this.apiService = apiService;
    }
    getPolicy(organizationId, type) {
        return bw_policy_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + organizationId + "/policies/" + type, null, true, true);
            return new bw_PolicyResponse(r);
        });
    }
    getPolicies(organizationId) {
        return bw_policy_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" + organizationId + "/policies", null, true, true);
            return new bw_ListResponse(r, bw_PolicyResponse);
        });
    }
    getPoliciesByToken(organizationId, token, email, organizationUserId) {
        return bw_policy_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/organizations/" +
                organizationId +
                "/policies/token?" +
                "token=" +
                encodeURIComponent(token) +
                "&email=" +
                bw_utils_Utils.encodeRFC3986URIComponent(email) +
                "&organizationUserId=" +
                organizationUserId, null, false, true);
            return bw_Policy.fromListResponse(new bw_ListResponse(r, bw_PolicyResponse));
        });
    }
    getMasterPasswordPolicyResponseForOrgUser(organizationId) {
        return bw_policy_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.apiService.send("GET", "/organizations/" + organizationId + "/policies/master-password", null, true, true);
            return new bw_PolicyResponse(response);
        });
    }
    getMasterPasswordPolicyOptsForOrgUser(orgId) {
        return bw_policy_api_service_awaiter(this, void 0, void 0, function* () {
            try {
                const masterPasswordPolicyResponse = yield this.getMasterPasswordPolicyResponseForOrgUser(orgId);
                const masterPasswordPolicy = bw_Policy.fromResponse(masterPasswordPolicyResponse);
                if (!masterPasswordPolicy) {
                    return null;
                }
                return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.policyService.masterPasswordPolicyOptions$([masterPasswordPolicy]));
            }
            catch (error) {
                // If policy not found, return null
                if (error instanceof bw_ErrorResponse && error.statusCode === bw_HttpStatusCode.NotFound) {
                    return null;
                }
                // otherwise rethrow error
                throw error;
            }
        });
    }
    putPolicy(organizationId, type, request) {
        return bw_policy_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/organizations/" + organizationId + "/policies/" + type, request, true, true);
            const response = new bw_PolicyResponse(r);
            const data = new bw_PolicyData(response);
            yield this.policyService.upsert(data);
        });
    }
}

;// ../../libs/common/src/admin-console/models/domain/reset-password-policy-options.ts

class bw_ResetPasswordPolicyOptions extends bw_domain_base_Domain {
    constructor() {
        super(...arguments);
        this.autoEnrollEnabled = false;
    }
}

;// ../../libs/common/src/admin-console/services/policy/policy.service.ts
var bw_policy_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






const bw_policyRecordToArray = (policiesMap) => Object.values(policiesMap || {}).map((f) => new bw_Policy(f));
const bw_POLICIES = bw_UserKeyDefinition.record(bw_POLICIES_DISK, "policies", {
    deserializer: (policyData) => policyData,
    clearOn: ["logout"],
});
class bw_PolicyService {
    constructor(stateProvider, organizationService) {
        this.stateProvider = stateProvider;
        this.organizationService = organizationService;
        this.activeUserPolicyState = this.stateProvider.getActive(bw_POLICIES);
        this.activeUserPolicies$ = this.activeUserPolicyState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((policyData) => bw_policyRecordToArray(policyData)));
        this.policies$ = this.activeUserPolicies$;
    }
    get$(policyType) {
        const filteredPolicies$ = this.activeUserPolicies$.pipe((0,bw_external_rxjs_namespaceObject.map)((policies) => policies.filter((p) => p.type === policyType)));
        const organizations$ = this.stateProvider.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => this.organizationService.organizations$(userId)));
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([filteredPolicies$, organizations$]).pipe((0,bw_external_rxjs_namespaceObject.map)(([policies, organizations]) => { var _a, _b; return (_b = (_a = this.enforcedPolicyFilter(policies, organizations)) === null || _a === void 0 ? void 0 : _a.at(0)) !== null && _b !== void 0 ? _b : null; }));
    }
    getAll$(policyType, userId) {
        const filteredPolicies$ = this.stateProvider.getUserState$(bw_POLICIES, userId).pipe((0,bw_external_rxjs_namespaceObject.map)((policyData) => bw_policyRecordToArray(policyData)), (0,bw_external_rxjs_namespaceObject.map)((policies) => policies.filter((p) => p.type === policyType)));
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([filteredPolicies$, this.organizationService.organizations$(userId)]).pipe((0,bw_external_rxjs_namespaceObject.map)(([policies, organizations]) => this.enforcedPolicyFilter(policies, organizations)));
    }
    getAll(policyType) {
        return bw_policy_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.policies$.pipe((0,bw_external_rxjs_namespaceObject.map)((policies) => policies.filter((p) => p.type === policyType))));
        });
    }
    policyAppliesToActiveUser$(policyType) {
        return this.get$(policyType).pipe((0,bw_external_rxjs_namespaceObject.map)((policy) => policy != null));
    }
    policyAppliesToUser(policyType) {
        return bw_policy_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.policyAppliesToActiveUser$(policyType));
        });
    }
    enforcedPolicyFilter(policies, organizations) {
        const orgDict = Object.fromEntries(organizations.map((o) => [o.id, o]));
        return policies.filter((policy) => {
            const organization = orgDict[policy.organizationId];
            // This shouldn't happen, i.e. the user should only have policies for orgs they are a member of
            // But if it does, err on the side of enforcing the policy
            if (organization == null) {
                return true;
            }
            return (policy.enabled &&
                organization.status >= bw_OrganizationUserStatusType.Accepted &&
                organization.usePolicies &&
                !this.isExemptFromPolicy(policy.type, organization));
        });
    }
    masterPasswordPolicyOptions$(policies) {
        const observable = policies ? (0,bw_external_rxjs_namespaceObject.of)(policies) : this.policies$;
        return observable.pipe((0,bw_external_rxjs_namespaceObject.map)((obsPolicies) => {
            let enforcedOptions = null;
            const filteredPolicies = obsPolicies.filter((p) => p.type === bw_policy_type_enum_PolicyType.MasterPassword);
            if (filteredPolicies == null || filteredPolicies.length === 0) {
                return enforcedOptions;
            }
            filteredPolicies.forEach((currentPolicy) => {
                if (!currentPolicy.enabled || currentPolicy.data == null) {
                    return;
                }
                if (enforcedOptions == null) {
                    enforcedOptions = new bw_MasterPasswordPolicyOptions();
                }
                if (currentPolicy.data.minComplexity != null &&
                    currentPolicy.data.minComplexity > enforcedOptions.minComplexity) {
                    enforcedOptions.minComplexity = currentPolicy.data.minComplexity;
                }
                if (currentPolicy.data.minLength != null &&
                    currentPolicy.data.minLength > enforcedOptions.minLength) {
                    enforcedOptions.minLength = currentPolicy.data.minLength;
                }
                if (currentPolicy.data.requireUpper) {
                    enforcedOptions.requireUpper = true;
                }
                if (currentPolicy.data.requireLower) {
                    enforcedOptions.requireLower = true;
                }
                if (currentPolicy.data.requireNumbers) {
                    enforcedOptions.requireNumbers = true;
                }
                if (currentPolicy.data.requireSpecial) {
                    enforcedOptions.requireSpecial = true;
                }
                if (currentPolicy.data.enforceOnLogin) {
                    enforcedOptions.enforceOnLogin = true;
                }
            });
            return enforcedOptions;
        }));
    }
    evaluateMasterPassword(passwordStrength, newPassword, enforcedPolicyOptions) {
        if (enforcedPolicyOptions == null) {
            return true;
        }
        if (enforcedPolicyOptions.minComplexity > 0 &&
            enforcedPolicyOptions.minComplexity > passwordStrength) {
            return false;
        }
        if (enforcedPolicyOptions.minLength > 0 &&
            enforcedPolicyOptions.minLength > newPassword.length) {
            return false;
        }
        if (enforcedPolicyOptions.requireUpper && newPassword.toLocaleLowerCase() === newPassword) {
            return false;
        }
        if (enforcedPolicyOptions.requireLower && newPassword.toLocaleUpperCase() === newPassword) {
            return false;
        }
        if (enforcedPolicyOptions.requireNumbers && !/[0-9]/.test(newPassword)) {
            return false;
        }
        // eslint-disable-next-line
        if (enforcedPolicyOptions.requireSpecial && !/[!@#$%\^&*]/g.test(newPassword)) {
            return false;
        }
        return true;
    }
    getResetPasswordPolicyOptions(policies, orgId) {
        var _a, _b, _c;
        const resetPasswordPolicyOptions = new bw_ResetPasswordPolicyOptions();
        if (policies == null || orgId == null) {
            return [resetPasswordPolicyOptions, false];
        }
        const policy = policies.find((p) => p.organizationId === orgId && p.type === bw_policy_type_enum_PolicyType.ResetPassword && p.enabled);
        resetPasswordPolicyOptions.autoEnrollEnabled = (_b = (_a = policy === null || policy === void 0 ? void 0 : policy.data) === null || _a === void 0 ? void 0 : _a.autoEnrollEnabled) !== null && _b !== void 0 ? _b : false;
        return [resetPasswordPolicyOptions, (_c = policy === null || policy === void 0 ? void 0 : policy.enabled) !== null && _c !== void 0 ? _c : false];
    }
    upsert(policy) {
        return bw_policy_service_awaiter(this, void 0, void 0, function* () {
            yield this.activeUserPolicyState.update((policies) => {
                policies !== null && policies !== void 0 ? policies : (policies = {});
                policies[policy.id] = policy;
                return policies;
            });
        });
    }
    replace(policies, userId) {
        return bw_policy_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_POLICIES, policies, userId);
        });
    }
    /**
     * Determines whether an orgUser is exempt from a specific policy because of their role
     * Generally orgUsers who can manage policies are exempt from them, but some policies are stricter
     */
    isExemptFromPolicy(policyType, organization) {
        switch (policyType) {
            case bw_policy_type_enum_PolicyType.MaximumVaultTimeout:
                // Max Vault Timeout applies to everyone except owners
                return organization.isOwner;
            case bw_policy_type_enum_PolicyType.PasswordGenerator:
                // password generation policy applies to everyone
                return false;
            case bw_policy_type_enum_PolicyType.PersonalOwnership:
                // individual vault policy applies to everyone except admins and owners
                return organization.isAdmin;
            case bw_policy_type_enum_PolicyType.FreeFamiliesSponsorshipPolicy:
                // free Bitwarden families policy applies to everyone
                return false;
            case bw_policy_type_enum_PolicyType.RemoveUnlockWithPin:
                // free Remove Unlock with PIN policy applies to everyone
                return false;
            default:
                return organization.canManagePolicies;
        }
    }
}

;// ../../libs/common/src/admin-console/models/response/addable-organization.response.ts

class bw_AddableOrganizationResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("id");
        this.plan = this.getResponseProperty("plan");
        this.name = this.getResponseProperty("name");
        this.seats = this.getResponseProperty("seats");
        this.disabled = this.getResponseProperty("disabled");
    }
}

;// ../../libs/common/src/admin-console/models/response/provider/provider.response.ts

class bw_ProviderResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.name = this.getResponseProperty("Name");
        this.businessName = this.getResponseProperty("BusinessName");
        this.billingEmail = this.getResponseProperty("BillingEmail");
        this.creationDate = this.getResponseProperty("CreationDate");
        this.type = this.getResponseProperty("Type");
    }
}

;// ../../libs/common/src/admin-console/services/provider/provider-api.service.ts
var bw_provider_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_ProviderApiService {
    constructor(apiService) {
        this.apiService = apiService;
    }
    postProviderSetup(id, request) {
        return bw_provider_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/providers/" + id + "/setup", request, true, true);
            return new bw_ProviderResponse(r);
        });
    }
    getProvider(id) {
        return bw_provider_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/providers/" + id, null, true, true);
            return new bw_ProviderResponse(r);
        });
    }
    putProvider(id, request) {
        return bw_provider_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/providers/" + id, request, true, true);
            return new bw_ProviderResponse(r);
        });
    }
    providerRecoverDeleteToken(providerId, request) {
        return this.apiService.send("POST", "/providers/" + providerId + "/delete-recover-token", request, false, false);
    }
    deleteProvider(id) {
        return bw_provider_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("DELETE", "/providers/" + id, null, true, false);
        });
    }
    getProviderAddableOrganizations(providerId) {
        return bw_provider_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.apiService.send("GET", "/providers/" + providerId + "/clients/addable", null, true, true);
            return response.map((data) => new bw_AddableOrganizationResponse(data));
        });
    }
    addOrganizationToProvider(providerId, request) {
        return this.apiService.send("POST", "/providers/" + providerId + "/clients/existing", request, true, false);
    }
}

;// ../../libs/common/src/admin-console/models/domain/provider.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_Provider {
    constructor(obj) {
        if (obj == null) {
            return;
        }
        this.id = obj.id;
        this.name = obj.name;
        this.status = obj.status;
        this.type = obj.type;
        this.enabled = obj.enabled;
        this.userId = obj.userId;
        this.useEvents = obj.useEvents;
        this.providerStatus = obj.providerStatus;
    }
    get canAccess() {
        if (this.isProviderAdmin) {
            return true;
        }
        return this.enabled && this.status === bw_ProviderUserStatusType.Confirmed;
    }
    get canCreateOrganizations() {
        return this.enabled && this.isProviderAdmin;
    }
    get canManageUsers() {
        return this.isProviderAdmin;
    }
    get canAccessEventLogs() {
        return this.isProviderAdmin;
    }
    get isProviderAdmin() {
        return this.type === bw_ProviderUserType.ProviderAdmin;
    }
}

;// ../../libs/common/src/admin-console/services/provider.service.ts
var bw_provider_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



const bw_PROVIDERS = bw_UserKeyDefinition.record(bw_PROVIDERS_DISK, "providers", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});
function bw_mapToSingleProvider(providerId) {
    return (0,bw_external_rxjs_namespaceObject.map)((providers) => providers === null || providers === void 0 ? void 0 : providers.find((p) => p.id === providerId));
}
class bw_ProviderService {
    constructor(stateProvider) {
        this.stateProvider = stateProvider;
    }
    providers$(userId) {
        // FIXME: Can be replaced with `getUserStateOrDefault$` if we weren't trying to pick this.
        return (userId != null
            ? this.stateProvider.getUser(userId, bw_PROVIDERS).state$
            : this.stateProvider.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.take)(1), (0,bw_external_rxjs_namespaceObject.switchMap)((userId) => userId != null ? this.stateProvider.getUser(userId, bw_PROVIDERS).state$ : (0,bw_external_rxjs_namespaceObject.of)(null)))).pipe(this.mapProviderRecordToArray());
    }
    mapProviderRecordToArray() {
        return (0,bw_external_rxjs_namespaceObject.map)((providers) => { var _a; return (_a = Object.values(providers !== null && providers !== void 0 ? providers : {})) === null || _a === void 0 ? void 0 : _a.map((o) => new bw_Provider(o)); });
    }
    get$(id) {
        return this.providers$().pipe(bw_mapToSingleProvider(id));
    }
    get(id) {
        return bw_provider_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.providers$().pipe(bw_mapToSingleProvider(id)));
        });
    }
    getAll() {
        return bw_provider_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.providers$());
        });
    }
    save(providers, userId) {
        return bw_provider_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_PROVIDERS, providers, userId);
        });
    }
}

;// ../../libs/common/src/auth/services/auth.service.ts
var bw_auth_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_AuthService {
    constructor(accountService, messageSender, keyService, apiService, stateService, tokenService) {
        this.accountService = accountService;
        this.messageSender = messageSender;
        this.keyService = keyService;
        this.apiService = apiService;
        this.stateService = stateService;
        this.tokenService = tokenService;
        this.activeAccountStatus$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id), (0,bw_external_rxjs_namespaceObject.switchMap)((userId) => {
            return this.authStatusFor$(userId);
        }));
        this.authStatuses$ = this.accountService.accounts$.pipe((0,bw_external_rxjs_namespaceObject.map)((accounts) => Object.keys(accounts)), (0,bw_external_rxjs_namespaceObject.switchMap)((entries) => {
            if (entries.length === 0) {
                return (0,bw_external_rxjs_namespaceObject.of)([]);
            }
            return (0,bw_external_rxjs_namespaceObject.combineLatest)(entries.map((userId) => this.authStatusFor$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((status) => ({ userId, status })))));
        }), (0,bw_external_rxjs_namespaceObject.map)((statuses) => {
            return statuses.reduce((acc, { userId, status }) => {
                acc[userId] = status;
                return acc;
            }, {});
        }));
    }
    authStatusFor$(userId) {
        if (!bw_utils_Utils.isGuid(userId)) {
            return (0,bw_external_rxjs_namespaceObject.of)(bw_authentication_status_AuthenticationStatus.LoggedOut);
        }
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.keyService.getInMemoryUserKeyFor$(userId),
            this.tokenService.hasAccessToken$(userId),
        ]).pipe((0,bw_external_rxjs_namespaceObject.map)(([userKey, hasAccessToken]) => {
            if (!hasAccessToken) {
                return bw_authentication_status_AuthenticationStatus.LoggedOut;
            }
            if (!userKey) {
                return bw_authentication_status_AuthenticationStatus.Locked;
            }
            return bw_authentication_status_AuthenticationStatus.Unlocked;
        }), (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(), (0,bw_external_rxjs_namespaceObject.shareReplay)({ bufferSize: 1, refCount: false }));
    }
    getAuthStatus(userId) {
        return bw_auth_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id))));
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authStatusFor$(userId));
        });
    }
    logOut(callback, userId) {
        callback();
        this.messageSender.send("loggedOut", { userId });
    }
}

;// ../../libs/common/src/models/request/update-avatar.request.ts
class bw_UpdateAvatarRequest {
    constructor(avatarColor) {
        this.avatarColor = avatarColor;
    }
}

;// ../../libs/common/src/auth/services/avatar.service.ts
var bw_avatar_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


const bw_AVATAR_COLOR = new bw_UserKeyDefinition(bw_AVATAR_DISK, "avatarColor", {
    deserializer: (value) => value,
    clearOn: [],
});
class bw_AvatarService {
    constructor(apiService, stateProvider) {
        this.apiService = apiService;
        this.stateProvider = stateProvider;
        this.avatarColor$ = this.stateProvider.getActive(bw_AVATAR_COLOR).state$;
    }
    setAvatarColor(color) {
        return bw_avatar_service_awaiter(this, void 0, void 0, function* () {
            const { avatarColor } = yield this.apiService.putAvatar(new bw_UpdateAvatarRequest(color));
            yield this.stateProvider.setUserState(bw_AVATAR_COLOR, avatarColor);
        });
    }
    setSyncAvatarColor(userId, color) {
        return bw_avatar_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_AVATAR_COLOR).update(() => color);
        });
    }
    getUserAvatarColor$(userId) {
        return this.stateProvider.getUser(userId, bw_AVATAR_COLOR).state$;
    }
}

;// ../../libs/common/src/auth/abstractions/devices/responses/device.response.ts

class bw_DeviceResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.userId = this.getResponseProperty("UserId");
        this.name = this.getResponseProperty("Name");
        this.identifier = this.getResponseProperty("Identifier");
        this.type = this.getResponseProperty("Type");
        this.creationDate = this.getResponseProperty("CreationDate");
        this.revisionDate = this.getResponseProperty("RevisionDate");
        this.isTrusted = this.getResponseProperty("IsTrusted");
        this.devicePendingAuthRequest = this.getResponseProperty("DevicePendingAuthRequest");
    }
}

;// ../../libs/common/src/auth/models/response/protected-device.response.ts


class bw_ProtectedDeviceResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("id");
        this.name = this.getResponseProperty("name");
        this.identifier = this.getResponseProperty("identifier");
        this.type = this.getResponseProperty("type");
        this.creationDate = new Date(this.getResponseProperty("creationDate"));
        if (response.encryptedUserKey) {
            this.encryptedUserKey = new bw_enc_string_EncString(this.getResponseProperty("encryptedUserKey"));
        }
        if (response.encryptedPublicKey) {
            this.encryptedPublicKey = new bw_enc_string_EncString(this.getResponseProperty("encryptedPublicKey"));
        }
    }
}

;// ../../libs/common/src/auth/services/devices/requests/trusted-device-keys.request.ts
class bw_TrustedDeviceKeysRequest {
    constructor(encryptedUserKey, encryptedPublicKey, encryptedPrivateKey) {
        this.encryptedUserKey = encryptedUserKey;
        this.encryptedPublicKey = encryptedPublicKey;
        this.encryptedPrivateKey = encryptedPrivateKey;
    }
}

;// ../../libs/common/src/auth/services/devices-api.service.implementation.ts
var bw_devices_api_service_implementation_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_DevicesApiServiceImplementation {
    constructor(apiService) {
        this.apiService = apiService;
    }
    getKnownDevice(email, deviceIdentifier) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/devices/knowndevice", null, false, true, null, (headers) => {
                headers.set("X-Device-Identifier", deviceIdentifier);
                headers.set("X-Request-Email", bw_utils_Utils.fromUtf8ToUrlB64(email));
            });
            return r;
        });
    }
    /**
     * Get device by identifier
     * @param deviceIdentifier - client generated id (not device id in DB)
     */
    getDeviceByIdentifier(deviceIdentifier) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", `/devices/identifier/${deviceIdentifier}`, null, true, true);
            return new bw_DeviceResponse(r);
        });
    }
    getDevices() {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/devices", null, true, true, null);
            return new bw_ListResponse(r, bw_DeviceResponse);
        });
    }
    updateTrustedDeviceKeys(deviceIdentifier, devicePublicKeyEncryptedUserKey, userKeyEncryptedDevicePublicKey, deviceKeyEncryptedDevicePrivateKey) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            const request = new bw_TrustedDeviceKeysRequest(devicePublicKeyEncryptedUserKey, userKeyEncryptedDevicePublicKey, deviceKeyEncryptedDevicePrivateKey);
            const result = yield this.apiService.send("PUT", `/devices/${deviceIdentifier}/keys`, request, true, true);
            return new bw_DeviceResponse(result);
        });
    }
    updateTrust(updateDevicesTrustRequestModel, deviceIdentifier) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", "/devices/update-trust", updateDevicesTrustRequestModel, true, false, null, (headers) => {
                headers.set("Device-Identifier", deviceIdentifier);
            });
        });
    }
    getDeviceKeys(deviceIdentifier, secretVerificationRequest) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            const result = yield this.apiService.send("POST", `/devices/${deviceIdentifier}/retrieve-keys`, secretVerificationRequest, true, true);
            return new bw_ProtectedDeviceResponse(result);
        });
    }
    postDeviceTrustLoss(deviceIdentifier) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", "/devices/lost-trust", null, true, false, null, (headers) => {
                headers.set("Device-Identifier", deviceIdentifier);
            });
        });
    }
    deactivateDevice(deviceId) {
        return bw_devices_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("POST", `/devices/${deviceId}/deactivate`, null, true, false);
        });
    }
}

;// ../../libs/common/src/auth/services/master-password/master-password-api.service.implementation.ts
var bw_master_password_api_service_implementation_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_MasterPasswordApiService {
    constructor(apiService, logService) {
        this.apiService = apiService;
        this.logService = logService;
    }
    setPassword(request) {
        return bw_master_password_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            try {
                const response = yield this.apiService.send("POST", "/accounts/set-password", request, true, false);
                return response;
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    postPassword(request) {
        return bw_master_password_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            try {
                const response = yield this.apiService.send("POST", "/accounts/password", request, true, false);
                return response;
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    putUpdateTempPassword(request) {
        return bw_master_password_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            try {
                const response = yield this.apiService.send("PUT", "/accounts/update-temp-password", request, true, false);
                return response;
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
    putUpdateTdeOffboardingPassword(request) {
        return bw_master_password_api_service_implementation_awaiter(this, void 0, void 0, function* () {
            try {
                const response = yield this.apiService.send("PUT", "/accounts/update-tde-offboarding-password", request, true, false);
                return response;
            }
            catch (e) {
                this.logService.error(e);
                throw e;
            }
        });
    }
}

;// ../../libs/common/src/auth/models/domain/set-tokens-result.ts
class bw_SetTokensResult {
    constructor(accessToken, refreshToken, clientIdSecretPair) {
        this.accessToken = accessToken;
        this.refreshToken = refreshToken;
        this.clientIdSecretPair = clientIdSecretPair;
    }
}

;// ../../libs/common/src/auth/services/token.state.ts

// Note: all tokens / API key information must be cleared on logout.
// because we are using secure storage, we must manually call to clean up our tokens.
// See stateService.deAuthenticateAccount for where we call clearTokens(...)
const bw_ACCESS_TOKEN_DISK = new bw_UserKeyDefinition(bw_TOKEN_DISK, "accessToken", {
    deserializer: (accessToken) => accessToken,
    clearOn: [], // Manually handled
});
const bw_ACCESS_TOKEN_MEMORY = new bw_UserKeyDefinition(bw_TOKEN_MEMORY, "accessToken", {
    deserializer: (accessToken) => accessToken,
    clearOn: [], // Manually handled
});
const bw_REFRESH_TOKEN_DISK = new bw_UserKeyDefinition(bw_TOKEN_DISK, "refreshToken", {
    deserializer: (refreshToken) => refreshToken,
    clearOn: [], // Manually handled
});
const bw_REFRESH_TOKEN_MEMORY = new bw_UserKeyDefinition(bw_TOKEN_MEMORY, "refreshToken", {
    deserializer: (refreshToken) => refreshToken,
    clearOn: [], // Manually handled
});
const bw_EMAIL_TWO_FACTOR_TOKEN_RECORD_DISK_LOCAL = bw_KeyDefinition.record(bw_TOKEN_DISK_LOCAL, "emailTwoFactorTokenRecord", {
    deserializer: (emailTwoFactorTokenRecord) => emailTwoFactorTokenRecord,
});
const bw_API_KEY_CLIENT_ID_DISK = new bw_UserKeyDefinition(bw_TOKEN_DISK, "apiKeyClientId", {
    deserializer: (apiKeyClientId) => apiKeyClientId,
    clearOn: [], // Manually handled
});
const bw_API_KEY_CLIENT_ID_MEMORY = new bw_UserKeyDefinition(bw_TOKEN_MEMORY, "apiKeyClientId", {
    deserializer: (apiKeyClientId) => apiKeyClientId,
    clearOn: [], // Manually handled
});
const bw_API_KEY_CLIENT_SECRET_DISK = new bw_UserKeyDefinition(bw_TOKEN_DISK, "apiKeyClientSecret", {
    deserializer: (apiKeyClientSecret) => apiKeyClientSecret,
    clearOn: [], // Manually handled
});
const bw_API_KEY_CLIENT_SECRET_MEMORY = new bw_UserKeyDefinition(bw_TOKEN_MEMORY, "apiKeyClientSecret", {
    deserializer: (apiKeyClientSecret) => apiKeyClientSecret,
    clearOn: [], // Manually handled
});
const bw_SECURITY_STAMP_MEMORY = new bw_UserKeyDefinition(bw_TOKEN_MEMORY, "securityStamp", {
    deserializer: (securityStamp) => securityStamp,
    clearOn: ["logout"],
});

;// ../../libs/common/src/auth/services/token.service.ts
var bw_token_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










var bw_TokenStorageLocation;
(function (TokenStorageLocation) {
    TokenStorageLocation["Disk"] = "disk";
    TokenStorageLocation["SecureStorage"] = "secureStorage";
    TokenStorageLocation["Memory"] = "memory";
})(bw_TokenStorageLocation || (bw_TokenStorageLocation = {}));
class bw_TokenService {
    constructor(
    // Note: we cannot use ActiveStateProvider because if we ever want to inject
    // this service into the AccountService, we will make a circular dependency
    singleUserStateProvider, globalStateProvider, platformSupportsSecureStorage, secureStorageService, keyGenerationService, encryptService, logService, logoutCallback) {
        this.singleUserStateProvider = singleUserStateProvider;
        this.globalStateProvider = globalStateProvider;
        this.platformSupportsSecureStorage = platformSupportsSecureStorage;
        this.secureStorageService = secureStorageService;
        this.keyGenerationService = keyGenerationService;
        this.encryptService = encryptService;
        this.logService = logService;
        this.logoutCallback = logoutCallback;
        this.accessTokenKeySecureStorageKey = "_accessTokenKey";
        this.refreshTokenSecureStorageKey = "_refreshToken";
        this.initializeState();
    }
    hasAccessToken$(userId) {
        // FIXME Once once vault timeout action is observable, we can use it to determine storage location
        // and avoid the need to check both disk and memory.
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.singleUserStateProvider.get(userId, bw_ACCESS_TOKEN_DISK).state$,
            this.singleUserStateProvider.get(userId, bw_ACCESS_TOKEN_MEMORY).state$,
        ]).pipe((0,bw_external_rxjs_namespaceObject.map)(([disk, memory]) => Boolean(disk || memory)));
    }
    initializeState() {
        this.emailTwoFactorTokenRecordGlobalState = this.globalStateProvider.get(bw_EMAIL_TWO_FACTOR_TOKEN_RECORD_DISK_LOCAL);
        this.activeUserIdGlobalState = this.globalStateProvider.get(bw_ACCOUNT_ACTIVE_ACCOUNT_ID);
    }
    setTokens(accessToken, vaultTimeoutAction, vaultTimeout, refreshToken, clientIdClientSecret) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            if (!accessToken) {
                throw new Error("Access token is required.");
            }
            // Can't check for falsey b/c 0 is a valid value
            if (vaultTimeout == null) {
                throw new Error("Vault Timeout is required.");
            }
            if (vaultTimeoutAction == null) {
                throw new Error("Vault Timeout Action is required.");
            }
            // get user id the access token
            const userId = yield this.getUserIdFromAccessToken(accessToken);
            if (!userId) {
                throw new Error("User id not found. Cannot set tokens.");
            }
            const newAccessToken = yield this._setAccessToken(accessToken, vaultTimeoutAction, vaultTimeout, userId);
            const newTokens = new bw_SetTokensResult(newAccessToken);
            if (refreshToken) {
                newTokens.refreshToken = yield this.setRefreshToken(refreshToken, vaultTimeoutAction, vaultTimeout, userId);
            }
            if (clientIdClientSecret != null) {
                const clientId = yield this.setClientId(clientIdClientSecret[0], vaultTimeoutAction, vaultTimeout, userId);
                const clientSecret = yield this.setClientSecret(clientIdClientSecret[1], vaultTimeoutAction, vaultTimeout, userId);
                newTokens.clientIdSecretPair = [clientId, clientSecret];
            }
            return newTokens;
        });
    }
    getAccessTokenKey(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            const accessTokenKeyB64 = yield this.secureStorageService.get(`${userId}${this.accessTokenKeySecureStorageKey}`, this.getSecureStorageOptions(userId));
            if (!accessTokenKeyB64) {
                return null;
            }
            const accessTokenKey = bw_SymmetricCryptoKey.fromJSON(accessTokenKeyB64);
            return accessTokenKey;
        });
    }
    createAndSaveAccessTokenKey(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            const newAccessTokenKey = (yield this.keyGenerationService.createKey(512));
            yield this.secureStorageService.save(`${userId}${this.accessTokenKeySecureStorageKey}`, newAccessTokenKey, this.getSecureStorageOptions(userId));
            // We are having intermittent issues with access token keys not saving into secure storage on windows 10/11.
            // So, let's add a check to ensure we can read the value after writing it.
            const accessTokenKey = yield this.getAccessTokenKey(userId);
            if (!accessTokenKey) {
                throw new Error("New Access token key unable to be retrieved from secure storage.");
            }
            return newAccessTokenKey;
        });
    }
    clearAccessTokenKey(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            yield this.secureStorageService.remove(`${userId}${this.accessTokenKeySecureStorageKey}`, this.getSecureStorageOptions(userId));
        });
    }
    getOrCreateAccessTokenKey(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            if (!this.platformSupportsSecureStorage) {
                throw new Error("Platform does not support secure storage. Cannot obtain access token key.");
            }
            if (!userId) {
                throw new Error("User id not found. Cannot obtain access token key.");
            }
            // First see if we have an accessTokenKey in secure storage and return it if we do
            // Note: retrieving/saving data from/to secure storage on linux will throw if the
            // distro doesn't have a secure storage provider
            let accessTokenKey = yield this.getAccessTokenKey(userId);
            if (!accessTokenKey) {
                // Otherwise, create a new one and save it to secure storage, then return it
                accessTokenKey = yield this.createAndSaveAccessTokenKey(userId);
            }
            return accessTokenKey;
        });
    }
    encryptAccessToken(accessToken, userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            const accessTokenKey = yield this.getOrCreateAccessTokenKey(userId);
            return yield this.encryptService.encrypt(accessToken, accessTokenKey);
        });
    }
    decryptAccessToken(accessTokenKey, encryptedAccessToken) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            if (!accessTokenKey) {
                throw new Error("decryptAccessToken: Access token key required. Cannot decrypt access token.");
            }
            const decryptedAccessToken = yield this.encryptService.decryptToUtf8(encryptedAccessToken, accessTokenKey);
            return decryptedAccessToken;
        });
    }
    /**
     * Internal helper for set access token which always requires user id.
     * This is useful because setTokens always will have a user id from the access token whereas
     * the public setAccessToken method does not.
     */
    _setAccessToken(accessToken, vaultTimeoutAction, vaultTimeout, userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            const storageLocation = yield this.determineStorageLocation(vaultTimeoutAction, vaultTimeout, true);
            switch (storageLocation) {
                case bw_TokenStorageLocation.SecureStorage: {
                    // Secure storage implementations have variable length limitations (Windows), so we cannot
                    // store the access token directly. Instead, we encrypt with accessTokenKey and store that
                    // in secure storage.
                    let decryptedAccessToken = null;
                    try {
                        const encryptedAccessToken = yield this.encryptAccessToken(accessToken, userId);
                        // Save the encrypted access token to disk
                        yield this.singleUserStateProvider
                            .get(userId, bw_ACCESS_TOKEN_DISK)
                            .update((_) => encryptedAccessToken.encryptedString);
                        // If we've successfully stored the encrypted access token to disk, we can return the decrypted access token
                        // so that the caller can use it immediately.
                        decryptedAccessToken = accessToken;
                        // TODO: PM-6408
                        // 2024-02-20: Remove access token from memory so that we migrate to encrypt the access token over time.
                        // Remove this call to remove the access token from memory after 3 months.
                        yield this.singleUserStateProvider.get(userId, bw_ACCESS_TOKEN_MEMORY).update((_) => null);
                    }
                    catch (error) {
                        this.logService.error(`SetAccessToken: storing encrypted access token in secure storage failed. Falling back to disk storage.`, error);
                        // Fall back to disk storage for unecrypted access token
                        decryptedAccessToken = yield this.singleUserStateProvider
                            .get(userId, bw_ACCESS_TOKEN_DISK)
                            .update((_) => accessToken);
                    }
                    return decryptedAccessToken;
                }
                case bw_TokenStorageLocation.Disk:
                    // Access token stored on disk unencrypted as platform does not support secure storage
                    return yield this.singleUserStateProvider
                        .get(userId, bw_ACCESS_TOKEN_DISK)
                        .update((_) => accessToken);
                case bw_TokenStorageLocation.Memory:
                    // Access token stored in memory due to vault timeout settings
                    return yield this.singleUserStateProvider
                        .get(userId, bw_ACCESS_TOKEN_MEMORY)
                        .update((_) => accessToken);
            }
        });
    }
    setAccessToken(accessToken, vaultTimeoutAction, vaultTimeout) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            if (!accessToken) {
                throw new Error("Access token is required.");
            }
            const userId = yield this.getUserIdFromAccessToken(accessToken);
            // If we don't have a user id, we can't save the value
            if (!userId) {
                throw new Error("User id not found. Cannot save access token.");
            }
            // Can't check for falsey b/c 0 is a valid value
            if (vaultTimeout == null) {
                throw new Error("Vault Timeout is required.");
            }
            if (vaultTimeoutAction == null) {
                throw new Error("Vault Timeout Action is required.");
            }
            return yield this._setAccessToken(accessToken, vaultTimeoutAction, vaultTimeout, userId);
        });
    }
    clearAccessToken(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            // If we don't have a user id, we can't clear the value
            if (!userId) {
                throw new Error("User id not found. Cannot clear access token.");
            }
            // TODO: re-eval this implementation once we get shared key definitions for vault timeout and vault timeout action data.
            // we can't determine storage location w/out vaultTimeoutAction and vaultTimeout
            // but we can simply clear all locations to avoid the need to require those parameters.
            if (this.platformSupportsSecureStorage) {
                // Always clear the access token key when clearing the access token
                // The next set of the access token will create a new access token key
                yield this.clearAccessTokenKey(userId);
            }
            // Platform doesn't support secure storage, so use state provider implementation
            yield this.singleUserStateProvider.get(userId, bw_ACCESS_TOKEN_DISK).update((_) => null);
            yield this.singleUserStateProvider.get(userId, bw_ACCESS_TOKEN_MEMORY).update((_) => null);
        });
    }
    getAccessToken(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                return null;
            }
            // Try to get the access token from memory
            const accessTokenMemory = yield this.getStateValueByUserIdAndKeyDef(userId, bw_ACCESS_TOKEN_MEMORY);
            if (accessTokenMemory != null) {
                return accessTokenMemory;
            }
            // If memory is null, read from disk
            const accessTokenDisk = yield this.getStateValueByUserIdAndKeyDef(userId, bw_ACCESS_TOKEN_DISK);
            if (!accessTokenDisk) {
                return null;
            }
            if (this.platformSupportsSecureStorage) {
                let accessTokenKey;
                try {
                    accessTokenKey = yield this.getAccessTokenKey(userId);
                }
                catch (error) {
                    if (bw_enc_string_EncString.isSerializedEncString(accessTokenDisk)) {
                        this.logService.error("Access token key retrieval failed. Unable to decrypt encrypted access token. Logging user out.", error);
                        yield this.logoutCallback("accessTokenUnableToBeDecrypted", userId);
                        return null;
                    }
                    // If the access token key is not found, but the access token is unencrypted then
                    // this indicates that this is the pre-migration state where the access token
                    // was stored unencrypted on disk. We can return the access token as is.
                    // Note: this is likely to only be hit for linux users who don't
                    // have a secure storage provider configured.
                    return accessTokenDisk;
                }
                if (!accessTokenKey) {
                    if (bw_enc_string_EncString.isSerializedEncString(accessTokenDisk)) {
                        // The access token is encrypted but we don't have the key to decrypt it for
                        // whatever reason so we have to log the user out.
                        this.logService.error("Access token key not found to decrypt encrypted access token. Logging user out.");
                        yield this.logoutCallback("accessTokenUnableToBeDecrypted", userId);
                        return null;
                    }
                    // We know this is an unencrypted access token
                    return accessTokenDisk;
                }
                try {
                    const encryptedAccessTokenEncString = new bw_enc_string_EncString(accessTokenDisk);
                    const decryptedAccessToken = yield this.decryptAccessToken(accessTokenKey, encryptedAccessTokenEncString);
                    return decryptedAccessToken;
                }
                catch (error) {
                    // If an error occurs during decryption, logout and then return null.
                    // We don't try to recover here since we'd like to know
                    // if access token and key are getting out of sync.
                    this.logService.error(`Failed to decrypt access token`, error);
                    yield this.logoutCallback("accessTokenUnableToBeDecrypted", userId);
                    return null;
                }
            }
            return accessTokenDisk;
        });
    }
    // Private because we only ever set the refresh token when also setting the access token
    // and we need the user id from the access token to save to secure storage
    setRefreshToken(refreshToken, vaultTimeoutAction, vaultTimeout, userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            // If we don't have a user id, we can't save the value
            if (!userId) {
                throw new Error("User id not found. Cannot save refresh token.");
            }
            // Can't check for falsey b/c 0 is a valid value
            if (vaultTimeout == null) {
                throw new Error("Vault Timeout is required.");
            }
            if (vaultTimeoutAction == null) {
                throw new Error("Vault Timeout Action is required.");
            }
            const storageLocation = yield this.determineStorageLocation(vaultTimeoutAction, vaultTimeout, true);
            switch (storageLocation) {
                case bw_TokenStorageLocation.SecureStorage: {
                    let decryptedRefreshToken = null;
                    try {
                        yield this.saveStringToSecureStorage(userId, this.refreshTokenSecureStorageKey, refreshToken);
                        // Check if the refresh token was able to be saved to secure storage by reading it
                        // immediately after setting it. This is needed due to intermittent silent failures on Windows 10/11.
                        const refreshTokenSecureStorage = yield this.getStringFromSecureStorage(userId, this.refreshTokenSecureStorageKey);
                        // Only throw if the refresh token was not saved to secure storage
                        // If we only check for a nullish value out of secure storage without considering the input value,
                        // then we would end up falling back to disk storage if the input value was null.
                        if (refreshToken !== null && !refreshTokenSecureStorage) {
                            throw new Error("Refresh token failed to save to secure storage.");
                        }
                        // If we've successfully stored the encrypted refresh token, we can return the decrypted refresh token
                        // so that the caller can use it immediately.
                        decryptedRefreshToken = refreshToken;
                        // TODO: PM-6408
                        // 2024-02-20: Remove refresh token from memory and disk so that we migrate to secure storage over time.
                        // Remove these 2 calls to remove the refresh token from memory and disk after 3 months.
                        yield this.singleUserStateProvider.get(userId, bw_REFRESH_TOKEN_DISK).update((_) => null);
                        yield this.singleUserStateProvider.get(userId, bw_REFRESH_TOKEN_MEMORY).update((_) => null);
                    }
                    catch (error) {
                        // This case could be hit for both Linux users who don't have secure storage configured
                        // or for Windows users who have intermittent issues with secure storage.
                        this.logService.error(`SetRefreshToken: storing refresh token in secure storage failed. Falling back to disk storage.`, error);
                        // Fall back to disk storage for refresh token
                        decryptedRefreshToken = yield this.singleUserStateProvider
                            .get(userId, bw_REFRESH_TOKEN_DISK)
                            .update((_) => refreshToken);
                    }
                    return decryptedRefreshToken;
                }
                case bw_TokenStorageLocation.Disk:
                    return yield this.singleUserStateProvider
                        .get(userId, bw_REFRESH_TOKEN_DISK)
                        .update((_) => refreshToken);
                case bw_TokenStorageLocation.Memory:
                    return yield this.singleUserStateProvider
                        .get(userId, bw_REFRESH_TOKEN_MEMORY)
                        .update((_) => refreshToken);
            }
        });
    }
    getRefreshToken(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                return null;
            }
            // pre-secure storage migration:
            // Always read memory first b/c faster
            const refreshTokenMemory = yield this.getStateValueByUserIdAndKeyDef(userId, bw_REFRESH_TOKEN_MEMORY);
            if (refreshTokenMemory != null) {
                return refreshTokenMemory;
            }
            // if memory is null, read from disk and then secure storage
            const refreshTokenDisk = yield this.getStateValueByUserIdAndKeyDef(userId, bw_REFRESH_TOKEN_DISK);
            if (refreshTokenDisk != null) {
                // This handles the scenario pre-secure storage migration where the refresh token was stored on disk.
                return refreshTokenDisk;
            }
            if (this.platformSupportsSecureStorage) {
                try {
                    const refreshTokenSecureStorage = yield this.getStringFromSecureStorage(userId, this.refreshTokenSecureStorageKey);
                    if (refreshTokenSecureStorage != null) {
                        return refreshTokenSecureStorage;
                    }
                    this.logService.error("Refresh token not found in secure storage. Access token will fail to refresh upon expiration or manual refresh.");
                }
                catch (error) {
                    // This case will be hit for Linux users who don't have secure storage configured.
                    this.logService.error(`Failed to retrieve refresh token from secure storage`, error);
                    yield this.logoutCallback("refreshTokenSecureStorageRetrievalFailure", userId);
                }
            }
            return null;
        });
    }
    clearRefreshToken(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            // If we don't have a user id, we can't clear the value
            if (!userId) {
                throw new Error("User id not found. Cannot clear refresh token.");
            }
            // TODO: re-eval this once we get shared key definitions for vault timeout and vault timeout action data.
            // we can't determine storage location w/out vaultTimeoutAction and vaultTimeout
            // but we can simply clear all locations to avoid the need to require those parameters
            if (this.platformSupportsSecureStorage) {
                yield this.secureStorageService.remove(`${userId}${this.refreshTokenSecureStorageKey}`, this.getSecureStorageOptions(userId));
            }
            // Platform doesn't support secure storage, so use state provider implementation
            yield this.singleUserStateProvider.get(userId, bw_REFRESH_TOKEN_MEMORY).update((_) => null);
            yield this.singleUserStateProvider.get(userId, bw_REFRESH_TOKEN_DISK).update((_) => null);
        });
    }
    setClientId(clientId, vaultTimeoutAction, vaultTimeout, userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            // If we don't have a user id, we can't save the value
            if (!userId) {
                throw new Error("User id not found. Cannot save client id.");
            }
            // Can't check for falsey b/c 0 is a valid value
            if (vaultTimeout == null) {
                throw new Error("Vault Timeout is required.");
            }
            if (vaultTimeoutAction == null) {
                throw new Error("Vault Timeout Action is required.");
            }
            const storageLocation = yield this.determineStorageLocation(vaultTimeoutAction, vaultTimeout, false);
            if (storageLocation === bw_TokenStorageLocation.Disk) {
                return yield this.singleUserStateProvider
                    .get(userId, bw_API_KEY_CLIENT_ID_DISK)
                    .update((_) => clientId);
            }
            else if (storageLocation === bw_TokenStorageLocation.Memory) {
                return yield this.singleUserStateProvider
                    .get(userId, bw_API_KEY_CLIENT_ID_MEMORY)
                    .update((_) => clientId);
            }
        });
    }
    getClientId(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                return undefined;
            }
            // Always read memory first b/c faster
            const apiKeyClientIdMemory = yield this.getStateValueByUserIdAndKeyDef(userId, bw_API_KEY_CLIENT_ID_MEMORY);
            if (apiKeyClientIdMemory != null) {
                return apiKeyClientIdMemory;
            }
            // if memory is null, read from disk
            return yield this.getStateValueByUserIdAndKeyDef(userId, bw_API_KEY_CLIENT_ID_DISK);
        });
    }
    clearClientId(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            // If we don't have a user id, we can't clear the value
            if (!userId) {
                throw new Error("User id not found. Cannot clear client id.");
            }
            // TODO: re-eval this once we get shared key definitions for vault timeout and vault timeout action data.
            // we can't determine storage location w/out vaultTimeoutAction and vaultTimeout
            // but we can simply clear both locations to avoid the need to require those parameters
            // Platform doesn't support secure storage, so use state provider implementation
            yield this.singleUserStateProvider.get(userId, bw_API_KEY_CLIENT_ID_MEMORY).update((_) => null);
            yield this.singleUserStateProvider.get(userId, bw_API_KEY_CLIENT_ID_DISK).update((_) => null);
        });
    }
    setClientSecret(clientSecret, vaultTimeoutAction, vaultTimeout, userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                throw new Error("User id not found. Cannot save client secret.");
            }
            // Can't check for falsey b/c 0 is a valid value
            if (vaultTimeout == null) {
                throw new Error("Vault Timeout is required.");
            }
            if (vaultTimeoutAction == null) {
                throw new Error("Vault Timeout Action is required.");
            }
            const storageLocation = yield this.determineStorageLocation(vaultTimeoutAction, vaultTimeout, false);
            if (storageLocation === bw_TokenStorageLocation.Disk) {
                return yield this.singleUserStateProvider
                    .get(userId, bw_API_KEY_CLIENT_SECRET_DISK)
                    .update((_) => clientSecret);
            }
            else if (storageLocation === bw_TokenStorageLocation.Memory) {
                return yield this.singleUserStateProvider
                    .get(userId, bw_API_KEY_CLIENT_SECRET_MEMORY)
                    .update((_) => clientSecret);
            }
        });
    }
    getClientSecret(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                return undefined;
            }
            // Always read memory first b/c faster
            const apiKeyClientSecretMemory = yield this.getStateValueByUserIdAndKeyDef(userId, bw_API_KEY_CLIENT_SECRET_MEMORY);
            if (apiKeyClientSecretMemory != null) {
                return apiKeyClientSecretMemory;
            }
            // if memory is null, read from disk
            return yield this.getStateValueByUserIdAndKeyDef(userId, bw_API_KEY_CLIENT_SECRET_DISK);
        });
    }
    clearClientSecret(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            // If we don't have a user id, we can't clear the value
            if (!userId) {
                throw new Error("User id not found. Cannot clear client secret.");
            }
            // TODO: re-eval this once we get shared key definitions for vault timeout and vault timeout action data.
            // we can't determine storage location w/out vaultTimeoutAction and vaultTimeout
            // but we can simply clear both locations to avoid the need to require those parameters
            // Platform doesn't support secure storage, so use state provider implementation
            yield this.singleUserStateProvider
                .get(userId, bw_API_KEY_CLIENT_SECRET_MEMORY)
                .update((_) => null);
            yield this.singleUserStateProvider.get(userId, bw_API_KEY_CLIENT_SECRET_DISK).update((_) => null);
        });
    }
    setTwoFactorToken(email, twoFactorToken) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            yield this.emailTwoFactorTokenRecordGlobalState.update((emailTwoFactorTokenRecord) => {
                emailTwoFactorTokenRecord !== null && emailTwoFactorTokenRecord !== void 0 ? emailTwoFactorTokenRecord : (emailTwoFactorTokenRecord = {});
                emailTwoFactorTokenRecord[email] = twoFactorToken;
                return emailTwoFactorTokenRecord;
            });
        });
    }
    getTwoFactorToken(email) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            const emailTwoFactorTokenRecord = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.emailTwoFactorTokenRecordGlobalState.state$);
            if (!emailTwoFactorTokenRecord) {
                return null;
            }
            return emailTwoFactorTokenRecord[email];
        });
    }
    clearTwoFactorToken(email) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            yield this.emailTwoFactorTokenRecordGlobalState.update((emailTwoFactorTokenRecord) => {
                emailTwoFactorTokenRecord !== null && emailTwoFactorTokenRecord !== void 0 ? emailTwoFactorTokenRecord : (emailTwoFactorTokenRecord = {});
                delete emailTwoFactorTokenRecord[email];
                return emailTwoFactorTokenRecord;
            });
        });
    }
    // TODO: stop accepting optional userIds
    clearTokens(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                throw new Error("User id not found. Cannot clear tokens.");
            }
            yield Promise.all([
                this.clearAccessToken(userId),
                this.clearRefreshToken(userId),
                this.clearClientId(userId),
                this.clearClientSecret(userId),
            ]);
        });
    }
    // jwthelper methods
    // ref https://github.com/auth0/angular-jwt/blob/master/src/angularJwt/services/jwt.js
    decodeAccessToken(tokenOrUserId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let token = tokenOrUserId;
            if (bw_utils_Utils.isGuid(tokenOrUserId)) {
                token = yield this.getAccessToken(tokenOrUserId);
            }
            else {
                token !== null && token !== void 0 ? token : (token = yield this.getAccessToken());
            }
            if (token == null) {
                throw new Error("Access token not found.");
            }
            return bw_decodeJwtTokenToJson(token);
        });
    }
    // TODO: PM-6678- tech debt - consider consolidating the return types of all these access
    // token data retrieval methods to return null if something goes wrong instead of throwing an error.
    getTokenExpirationDate() {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken();
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            // per RFC, exp claim is optional but if it exists, it should be a number
            if (!decoded || typeof decoded.exp !== "number") {
                return null;
            }
            // The 0 in Date(0) is the key; it sets the date to the epoch
            const expirationDate = new Date(0);
            expirationDate.setUTCSeconds(decoded.exp);
            return expirationDate;
        });
    }
    tokenSecondsRemaining() {
        return bw_token_service_awaiter(this, arguments, void 0, function* (offsetSeconds = 0) {
            const date = yield this.getTokenExpirationDate();
            if (date == null) {
                return 0;
            }
            const msRemaining = date.valueOf() - (new Date().valueOf() + offsetSeconds * 1000);
            return Math.round(msRemaining / 1000);
        });
    }
    tokenNeedsRefresh() {
        return bw_token_service_awaiter(this, arguments, void 0, function* (minutes = 5) {
            const sRemaining = yield this.tokenSecondsRemaining();
            return sRemaining < 60 * minutes;
        });
    }
    getUserId() {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken();
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            if (!decoded || typeof decoded.sub !== "string") {
                throw new Error("No user id found");
            }
            return decoded.sub;
        });
    }
    getUserIdFromAccessToken(accessToken) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken(accessToken);
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            if (!decoded || typeof decoded.sub !== "string") {
                throw new Error("No user id found");
            }
            return decoded.sub;
        });
    }
    getEmail() {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken();
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            if (!decoded || typeof decoded.email !== "string") {
                throw new Error("No email found");
            }
            return decoded.email;
        });
    }
    getEmailVerified() {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken();
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            if (!decoded || typeof decoded.email_verified !== "boolean") {
                throw new Error("No email verification found");
            }
            return decoded.email_verified;
        });
    }
    getName() {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken();
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            if (!decoded || typeof decoded.name !== "string") {
                return null;
            }
            return decoded.name;
        });
    }
    getIssuer() {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken();
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            if (!decoded || typeof decoded.iss !== "string") {
                throw new Error("No issuer found");
            }
            return decoded.iss;
        });
    }
    getIsExternal(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            let decoded;
            try {
                decoded = yield this.decodeAccessToken(userId);
            }
            catch (error) {
                throw new Error("Failed to decode access token: " + error.message);
            }
            return Array.isArray(decoded.amr) && decoded.amr.includes("external");
        });
    }
    getSecurityStamp(userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                throw new Error("User id not found. Cannot get security stamp.");
            }
            const securityStamp = yield this.getStateValueByUserIdAndKeyDef(userId, bw_SECURITY_STAMP_MEMORY);
            return securityStamp;
        });
    }
    setSecurityStamp(securityStamp, userId) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserIdGlobalState.state$));
            if (!userId) {
                throw new Error("User id not found. Cannot set security stamp.");
            }
            yield this.singleUserStateProvider
                .get(userId, bw_SECURITY_STAMP_MEMORY)
                .update((_) => securityStamp);
        });
    }
    getStateValueByUserIdAndKeyDef(userId, storageLocation) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            // read from single user state provider
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.singleUserStateProvider.get(userId, storageLocation).state$);
        });
    }
    determineStorageLocation(vaultTimeoutAction, vaultTimeout, useSecureStorage) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            if (vaultTimeoutAction == null) {
                throw new Error("TokenService - determineStorageLocation: We expect the vault timeout action to always exist at this point.");
            }
            if (vaultTimeout == null) {
                throw new Error("TokenService - determineStorageLocation: We expect the vault timeout to always exist at this point.");
            }
            if (vaultTimeoutAction === bw_VaultTimeoutAction.LogOut &&
                vaultTimeout !== bw_VaultTimeoutStringType.Never) {
                return bw_TokenStorageLocation.Memory;
            }
            else {
                if (useSecureStorage && this.platformSupportsSecureStorage) {
                    return bw_TokenStorageLocation.SecureStorage;
                }
                return bw_TokenStorageLocation.Disk;
            }
        });
    }
    saveStringToSecureStorage(userId, storageKey, value) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            yield this.secureStorageService.save(`${userId}${storageKey}`, value, this.getSecureStorageOptions(userId));
        });
    }
    getStringFromSecureStorage(userId, storageKey) {
        return bw_token_service_awaiter(this, void 0, void 0, function* () {
            // If we have a user ID, read from secure storage.
            return yield this.secureStorageService.get(`${userId}${storageKey}`, this.getSecureStorageOptions(userId));
        });
    }
    getSecureStorageOptions(userId) {
        return {
            storageLocation: bw_StorageLocation.Disk,
            useSecureStorage: true,
            userId: userId,
        };
    }
}

;// ../../libs/common/src/auth/services/two-factor.service.ts
var bw_two_factor_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




const bw_TwoFactorProviders = {
    [bw_TwoFactorProviderType.Authenticator]: {
        type: bw_TwoFactorProviderType.Authenticator,
        name: null,
        description: null,
        priority: 1,
        sort: 2,
        premium: false,
    },
    [bw_TwoFactorProviderType.Yubikey]: {
        type: bw_TwoFactorProviderType.Yubikey,
        name: null,
        description: null,
        priority: 3,
        sort: 4,
        premium: true,
    },
    [bw_TwoFactorProviderType.Duo]: {
        type: bw_TwoFactorProviderType.Duo,
        name: "Duo",
        description: null,
        priority: 2,
        sort: 5,
        premium: true,
    },
    [bw_TwoFactorProviderType.OrganizationDuo]: {
        type: bw_TwoFactorProviderType.OrganizationDuo,
        name: "Duo (Organization)",
        description: null,
        priority: 10,
        sort: 6,
        premium: false,
    },
    [bw_TwoFactorProviderType.Email]: {
        type: bw_TwoFactorProviderType.Email,
        name: null,
        description: null,
        priority: 0,
        sort: 1,
        premium: false,
    },
    [bw_TwoFactorProviderType.WebAuthn]: {
        type: bw_TwoFactorProviderType.WebAuthn,
        name: null,
        description: null,
        priority: 4,
        sort: 3,
        premium: false,
    },
};
// Memory storage as only required during authentication process
const bw_two_factor_service_PROVIDERS = bw_KeyDefinition.record(bw_TWO_FACTOR_MEMORY, "providers", {
    deserializer: (obj) => obj,
});
// Memory storage as only required during authentication process
const bw_SELECTED_PROVIDER = new bw_KeyDefinition(bw_TWO_FACTOR_MEMORY, "selected", {
    deserializer: (obj) => obj,
});
class bw_TwoFactorService {
    constructor(i18nService, platformUtilsService, globalStateProvider) {
        this.i18nService = i18nService;
        this.platformUtilsService = platformUtilsService;
        this.globalStateProvider = globalStateProvider;
        this.providersState = this.globalStateProvider.get(bw_two_factor_service_PROVIDERS);
        this.selectedState = this.globalStateProvider.get(bw_SELECTED_PROVIDER);
        this.providers$ = this.providersState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((providers) => bw_utils_Utils.recordToMap(providers)));
        this.selected$ = this.selectedState.state$;
    }
    init() {
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Email].name = this.i18nService.t("emailTitle");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Email].description = this.i18nService.t("emailDescV2");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Authenticator].name =
            this.i18nService.t("authenticatorAppTitle");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Authenticator].description =
            this.i18nService.t("authenticatorAppDescV2");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Duo].description = this.i18nService.t("duoDescV2");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.OrganizationDuo].name =
            "Duo (" + this.i18nService.t("organization") + ")";
        bw_TwoFactorProviders[bw_TwoFactorProviderType.OrganizationDuo].description =
            this.i18nService.t("duoOrganizationDesc");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.WebAuthn].name = this.i18nService.t("webAuthnTitle");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.WebAuthn].description =
            this.i18nService.t("webAuthnDesc");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Yubikey].name = this.i18nService.t("yubiKeyTitleV2");
        bw_TwoFactorProviders[bw_TwoFactorProviderType.Yubikey].description =
            this.i18nService.t("yubiKeyDesc");
    }
    getSupportedProviders(win) {
        return bw_two_factor_service_awaiter(this, void 0, void 0, function* () {
            const data = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.providers$);
            const providers = [];
            if (data == null) {
                return providers;
            }
            if (data.has(bw_TwoFactorProviderType.OrganizationDuo) &&
                this.platformUtilsService.supportsDuo()) {
                providers.push(bw_TwoFactorProviders[bw_TwoFactorProviderType.OrganizationDuo]);
            }
            if (data.has(bw_TwoFactorProviderType.Authenticator)) {
                providers.push(bw_TwoFactorProviders[bw_TwoFactorProviderType.Authenticator]);
            }
            if (data.has(bw_TwoFactorProviderType.Yubikey)) {
                providers.push(bw_TwoFactorProviders[bw_TwoFactorProviderType.Yubikey]);
            }
            if (data.has(bw_TwoFactorProviderType.Duo) && this.platformUtilsService.supportsDuo()) {
                providers.push(bw_TwoFactorProviders[bw_TwoFactorProviderType.Duo]);
            }
            if (data.has(bw_TwoFactorProviderType.WebAuthn) &&
                this.platformUtilsService.supportsWebAuthn(win)) {
                providers.push(bw_TwoFactorProviders[bw_TwoFactorProviderType.WebAuthn]);
            }
            if (data.has(bw_TwoFactorProviderType.Email)) {
                providers.push(bw_TwoFactorProviders[bw_TwoFactorProviderType.Email]);
            }
            return providers;
        });
    }
    getDefaultProvider(webAuthnSupported) {
        return bw_two_factor_service_awaiter(this, void 0, void 0, function* () {
            const data = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.providers$);
            const selected = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.selected$);
            if (data == null) {
                return null;
            }
            if (selected != null && data.has(selected)) {
                return selected;
            }
            let providerType = null;
            let providerPriority = -1;
            data.forEach((_value, type) => {
                const provider = bw_TwoFactorProviders[type];
                if (provider != null && provider.priority > providerPriority) {
                    if (type === bw_TwoFactorProviderType.WebAuthn && !webAuthnSupported) {
                        return;
                    }
                    providerType = type;
                    providerPriority = provider.priority;
                }
            });
            return providerType;
        });
    }
    setSelectedProvider(type) {
        return bw_two_factor_service_awaiter(this, void 0, void 0, function* () {
            yield this.selectedState.update(() => type);
        });
    }
    clearSelectedProvider() {
        return bw_two_factor_service_awaiter(this, void 0, void 0, function* () {
            yield this.selectedState.update(() => null);
        });
    }
    setProviders(response) {
        return bw_two_factor_service_awaiter(this, void 0, void 0, function* () {
            yield this.providersState.update(() => response.twoFactorProviders2);
        });
    }
    clearProviders() {
        return bw_two_factor_service_awaiter(this, void 0, void 0, function* () {
            yield this.providersState.update(() => null);
        });
    }
    getProviders() {
        return (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.providers$);
    }
}

;// ../../libs/common/src/auth/services/user-verification/user-verification-api.service.ts
var bw_user_verification_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_UserVerificationApiService {
    constructor(apiService) {
        this.apiService = apiService;
    }
    postAccountVerifyOTP(request) {
        return this.apiService.send("POST", "/accounts/verify-otp", request, true, false);
    }
    postAccountRequestOTP() {
        return bw_user_verification_api_service_awaiter(this, void 0, void 0, function* () {
            return this.apiService.send("POST", "/accounts/request-otp", null, true, false);
        });
    }
    postAccountVerifyPassword(request) {
        return this.apiService.send("POST", "/accounts/verify-password", request, true, true);
    }
}

;// ../../libs/common/src/auth/models/request/verify-otp.request.ts
class bw_VerifyOTPRequest {
    constructor(OTP) {
        this.OTP = OTP;
    }
}

;// ../../libs/common/src/auth/types/verification.ts
function bw_verificationHasSecret(verification) {
    return "secret" in verification;
}

;// ../../libs/common/src/auth/services/user-verification/user-verification.service.ts
var bw_user_verification_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







/**
 * Used for general-purpose user verification throughout the app.
 * Use it to verify the input collected by UserVerificationComponent.
 */
class bw_UserVerificationService {
    constructor(keyService, accountService, masterPasswordService, i18nService, userVerificationApiService, userDecryptionOptionsService, pinService, kdfConfigService, biometricsService) {
        this.keyService = keyService;
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.i18nService = i18nService;
        this.userVerificationApiService = userVerificationApiService;
        this.userDecryptionOptionsService = userDecryptionOptionsService;
        this.pinService = pinService;
        this.kdfConfigService = kdfConfigService;
        this.biometricsService = biometricsService;
    }
    getAvailableVerificationOptions(verificationType) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const userId = (_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$))) === null || _a === void 0 ? void 0 : _a.id;
            if (verificationType === "client") {
                const [userHasMasterPassword, isPinDecryptionAvailable, biometricsStatus] = yield Promise.all([
                    this.hasMasterPasswordAndMasterKeyHash(userId),
                    this.pinService.isPinDecryptionAvailable(userId),
                    this.biometricsService.getBiometricsStatus(),
                ]);
                // note: we do not need to check this.platformUtilsService.supportsBiometric() because
                // we can just use the logic below which works for both desktop & the browser extension.
                return {
                    client: {
                        masterPassword: userHasMasterPassword,
                        pin: isPinDecryptionAvailable,
                        biometrics: biometricsStatus === bw_BiometricsStatus.Available,
                    },
                    server: {
                        masterPassword: false,
                        otp: false,
                    },
                };
            }
            else {
                // server
                // Don't check if have MP hash locally, because we are going to send the secret to the server to be verified.
                const userHasMasterPassword = yield this.hasMasterPassword(userId);
                return {
                    client: {
                        masterPassword: false,
                        pin: false,
                        biometrics: false,
                    },
                    server: { masterPassword: userHasMasterPassword, otp: !userHasMasterPassword },
                };
            }
        });
    }
    buildRequest(verification, requestClass, alreadyHashed) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            this.validateSecretInput(verification);
            const request = requestClass != null ? new requestClass() : new bw_SecretVerificationRequest();
            if (verification.type === bw_VerificationType.OTP) {
                request.otp = verification.secret;
            }
            else {
                const [userId, email] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => [a === null || a === void 0 ? void 0 : a.id, a === null || a === void 0 ? void 0 : a.email])));
                let masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
                if (!masterKey && !alreadyHashed) {
                    masterKey = yield this.keyService.makeMasterKey(verification.secret, email, yield this.kdfConfigService.getKdfConfig());
                }
                request.masterPasswordHash = alreadyHashed
                    ? verification.secret
                    : yield this.keyService.hashMasterKey(verification.secret, masterKey);
            }
            return request;
        });
    }
    verifyUser(verification) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            if (verification == null) {
                throw new Error("Verification is required.");
            }
            const [userId, email] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => [a === null || a === void 0 ? void 0 : a.id, a === null || a === void 0 ? void 0 : a.email])));
            if (bw_verificationHasSecret(verification)) {
                this.validateSecretInput(verification);
            }
            switch (verification.type) {
                case bw_VerificationType.OTP:
                    return this.verifyUserByOTP(verification);
                case bw_VerificationType.MasterPassword:
                    yield this.verifyUserByMasterPassword(verification, userId, email);
                    return true;
                case bw_VerificationType.PIN:
                    return this.verifyUserByPIN(verification, userId);
                case bw_VerificationType.Biometrics:
                    return this.verifyUserByBiometrics();
                default: {
                    // Compile-time check for exhaustive switch
                    const _exhaustiveCheck = verification;
                    return _exhaustiveCheck;
                }
            }
        });
    }
    verifyUserByOTP(verification) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            const request = new bw_VerifyOTPRequest(verification.secret);
            try {
                yield this.userVerificationApiService.postAccountVerifyOTP(request);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                throw new Error(this.i18nService.t("invalidVerificationCode"));
            }
            return true;
        });
    }
    verifyUserByMasterPassword(verification, userId, email) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            if (!verification.secret) {
                throw new Error("Master Password is required. Cannot verify user without a master password.");
            }
            if (!userId) {
                throw new Error("User ID is required. Cannot verify user by master password.");
            }
            if (!email) {
                throw new Error("Email is required. Cannot verify user by master password.");
            }
            const kdfConfig = yield this.kdfConfigService.getKdfConfig();
            if (!kdfConfig) {
                throw new Error("KDF config is required. Cannot verify user by master password.");
            }
            let masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            if (!masterKey) {
                masterKey = yield this.keyService.makeMasterKey(verification.secret, email, kdfConfig);
            }
            if (!masterKey) {
                throw new Error("Master key could not be created to verify the master password.");
            }
            let policyOptions;
            // Client-side verification
            if (yield this.hasMasterPasswordAndMasterKeyHash(userId)) {
                const passwordValid = yield this.keyService.compareKeyHash(verification.secret, masterKey, userId);
                if (!passwordValid) {
                    throw new Error(this.i18nService.t("invalidMasterPassword"));
                }
                policyOptions = null;
            }
            else {
                // Server-side verification
                const request = new bw_SecretVerificationRequest();
                const serverKeyHash = yield this.keyService.hashMasterKey(verification.secret, masterKey, bw_HashPurpose.ServerAuthorization);
                request.masterPasswordHash = serverKeyHash;
                try {
                    policyOptions = yield this.userVerificationApiService.postAccountVerifyPassword(request);
                    // FIXME: Remove when updating file. Eslint update
                    // eslint-disable-next-line @typescript-eslint/no-unused-vars
                }
                catch (e) {
                    throw new Error(this.i18nService.t("invalidMasterPassword"));
                }
            }
            const localKeyHash = yield this.keyService.hashMasterKey(verification.secret, masterKey, bw_HashPurpose.LocalAuthorization);
            yield this.masterPasswordService.setMasterKeyHash(localKeyHash, userId);
            yield this.masterPasswordService.setMasterKey(masterKey, userId);
            return { policyOptions, masterKey };
        });
    }
    verifyUserByPIN(verification, userId) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("User ID is required. Cannot verify user by PIN.");
            }
            const userKey = yield this.pinService.decryptUserKeyWithPin(verification.secret, userId);
            return userKey != null;
        });
    }
    verifyUserByBiometrics() {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            return this.biometricsService.authenticateWithBiometrics();
        });
    }
    requestOTP() {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            yield this.userVerificationApiService.postAccountRequestOTP();
        });
    }
    hasMasterPassword(userId) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            if (userId) {
                const decryptionOptions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userDecryptionOptionsService.userDecryptionOptionsById$(userId));
                if ((decryptionOptions === null || decryptionOptions === void 0 ? void 0 : decryptionOptions.hasMasterPassword) != undefined) {
                    return decryptionOptions.hasMasterPassword;
                }
            }
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userDecryptionOptionsService.hasMasterPassword$);
        });
    }
    hasMasterPasswordAndMasterKeyHash(userId) {
        return bw_user_verification_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            userId !== null && userId !== void 0 ? userId : (userId = (_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$))) === null || _a === void 0 ? void 0 : _a.id);
            return ((yield this.hasMasterPassword(userId)) &&
                (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKeyHash$(userId))) != null);
        });
    }
    validateSecretInput(verification) {
        if ((verification === null || verification === void 0 ? void 0 : verification.secret) == null || verification.secret === "") {
            switch (verification.type) {
                case bw_VerificationType.OTP:
                    throw new Error(this.i18nService.t("verificationCodeRequired"));
                case bw_VerificationType.MasterPassword:
                    throw new Error(this.i18nService.t("masterPasswordRequired"));
                case bw_VerificationType.PIN:
                    throw new Error(this.i18nService.t("pinRequired"));
            }
        }
    }
}

;// ../../libs/common/src/autofill/services/autofill-settings.service.ts
var bw_autofill_settings_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




const bw_AUTOFILL_ON_PAGE_LOAD = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "autofillOnPageLoad", {
    deserializer: (value) => value !== null && value !== void 0 ? value : false,
    clearOn: [],
});
const bw_AUTOFILL_ON_PAGE_LOAD_DEFAULT = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "autofillOnPageLoadDefault", {
    deserializer: (value) => value !== null && value !== void 0 ? value : false,
    clearOn: [],
});
const bw_AUTOFILL_ON_PAGE_LOAD_CALLOUT_DISMISSED = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "autofillOnPageLoadCalloutIsDismissed", {
    deserializer: (value) => value !== null && value !== void 0 ? value : false,
    clearOn: [],
});
const bw_AUTOFILL_ON_PAGE_LOAD_POLICY_TOAST_HAS_DISPLAYED = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "autofillOnPageLoadPolicyToastHasDisplayed", {
    deserializer: (value) => value !== null && value !== void 0 ? value : false,
    clearOn: [],
});
const bw_AUTO_COPY_TOTP = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "autoCopyTotp", {
    deserializer: (value) => value !== null && value !== void 0 ? value : true,
    clearOn: [],
});
const bw_INLINE_MENU_VISIBILITY = new bw_KeyDefinition(bw_AUTOFILL_SETTINGS_DISK_LOCAL, "inlineMenuVisibility", {
    deserializer: (value) => value !== null && value !== void 0 ? value : bw_AutofillOverlayVisibility.Off,
});
const bw_SHOW_INLINE_MENU_IDENTITIES = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "showInlineMenuIdentities", {
    deserializer: (value) => value !== null && value !== void 0 ? value : true,
    clearOn: [],
});
const bw_SHOW_INLINE_MENU_CARDS = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "showInlineMenuCards", {
    deserializer: (value) => value !== null && value !== void 0 ? value : true,
    clearOn: [],
});
const bw_ENABLE_CONTEXT_MENU = new bw_KeyDefinition(bw_AUTOFILL_SETTINGS_DISK, "enableContextMenu", {
    deserializer: (value) => value !== null && value !== void 0 ? value : true,
});
const bw_CLEAR_CLIPBOARD_DELAY = new bw_UserKeyDefinition(bw_AUTOFILL_SETTINGS_DISK_LOCAL, "clearClipboardDelay", {
    deserializer: (value) => value !== null && value !== void 0 ? value : bw_ClearClipboardDelay.Never,
    clearOn: [],
});
class bw_AutofillSettingsServiceAbstraction {
}
class bw_AutofillSettingsService {
    constructor(stateProvider, policyService) {
        this.stateProvider = stateProvider;
        this.policyService = policyService;
        this.autofillOnPageLoadState = this.stateProvider.getActive(bw_AUTOFILL_ON_PAGE_LOAD);
        this.autofillOnPageLoad$ = this.autofillOnPageLoadState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : false));
        this.autofillOnPageLoadDefaultState = this.stateProvider.getActive(bw_AUTOFILL_ON_PAGE_LOAD_DEFAULT);
        this.autofillOnPageLoadDefault$ = this.autofillOnPageLoadDefaultState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : true));
        this.autofillOnPageLoadCalloutIsDismissedState = this.stateProvider.getActive(bw_AUTOFILL_ON_PAGE_LOAD_CALLOUT_DISMISSED);
        this.autofillOnPageLoadCalloutIsDismissed$ =
            this.autofillOnPageLoadCalloutIsDismissedState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : false));
        this.activateAutofillOnPageLoadFromPolicy$ = this.policyService.policyAppliesToActiveUser$(bw_policy_type_enum_PolicyType.ActivateAutofill);
        this.autofillOnPageLoadPolicyToastHasDisplayedState = this.stateProvider.getActive(bw_AUTOFILL_ON_PAGE_LOAD_POLICY_TOAST_HAS_DISPLAYED);
        this.autofillOnPageLoadPolicyToastHasDisplayed$ =
            this.autofillOnPageLoadPolicyToastHasDisplayedState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : false));
        this.autoCopyTotpState = this.stateProvider.getActive(bw_AUTO_COPY_TOTP);
        this.autoCopyTotp$ = this.autoCopyTotpState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : true));
        this.inlineMenuVisibilityState = this.stateProvider.getGlobal(bw_INLINE_MENU_VISIBILITY);
        this.inlineMenuVisibility$ = this.inlineMenuVisibilityState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : bw_AutofillOverlayVisibility.Off));
        this.showInlineMenuIdentitiesState = this.stateProvider.getActive(bw_SHOW_INLINE_MENU_IDENTITIES);
        this.showInlineMenuIdentities$ = this.showInlineMenuIdentitiesState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : true));
        this.showInlineMenuCardsState = this.stateProvider.getActive(bw_SHOW_INLINE_MENU_CARDS);
        this.showInlineMenuCards$ = this.showInlineMenuCardsState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : true));
        this.enableContextMenuState = this.stateProvider.getGlobal(bw_ENABLE_CONTEXT_MENU);
        this.enableContextMenu$ = this.enableContextMenuState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : true));
        this.clearClipboardDelayState = this.stateProvider.getActive(bw_CLEAR_CLIPBOARD_DELAY);
        this.clearClipboardDelay$ = this.clearClipboardDelayState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : bw_ClearClipboardDelay.Never));
    }
    setAutofillOnPageLoad(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.autofillOnPageLoadState.update(() => newValue);
        });
    }
    setAutofillOnPageLoadDefault(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.autofillOnPageLoadDefaultState.update(() => newValue);
        });
    }
    setAutofillOnPageLoadCalloutIsDismissed(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.autofillOnPageLoadCalloutIsDismissedState.update(() => newValue);
        });
    }
    setAutofillOnPageLoadPolicyToastHasDisplayed(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.autofillOnPageLoadPolicyToastHasDisplayedState.update(() => newValue);
        });
    }
    setAutoCopyTotp(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.autoCopyTotpState.update(() => newValue);
        });
    }
    setInlineMenuVisibility(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.inlineMenuVisibilityState.update(() => newValue);
        });
    }
    setShowInlineMenuIdentities(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.showInlineMenuIdentitiesState.update(() => newValue);
        });
    }
    setShowInlineMenuCards(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.showInlineMenuCardsState.update(() => newValue);
        });
    }
    setEnableContextMenu(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.enableContextMenuState.update(() => newValue);
        });
    }
    setClearClipboardDelay(newValue) {
        return bw_autofill_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.clearClipboardDelayState.update(() => newValue);
        });
    }
}

;// ../../libs/common/src/autofill/services/domain-settings.service.ts
var bw_domain_settings_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





const bw_SHOW_FAVICONS = new bw_KeyDefinition(bw_DOMAIN_SETTINGS_DISK, "showFavicons", {
    deserializer: (value) => value !== null && value !== void 0 ? value : true,
});
// Domain exclusion list for notifications
const bw_NEVER_DOMAINS = new bw_KeyDefinition(bw_DOMAIN_SETTINGS_DISK, "neverDomains", {
    deserializer: (value) => value !== null && value !== void 0 ? value : null,
});
// Domain exclusion list for content script injections
const bw_BLOCKED_INTERACTIONS_URIS = new bw_KeyDefinition(bw_DOMAIN_SETTINGS_DISK, "blockedInteractionsUris", {
    deserializer: (value) => value !== null && value !== void 0 ? value : {},
});
const bw_EQUIVALENT_DOMAINS = new bw_UserKeyDefinition(bw_DOMAIN_SETTINGS_DISK, "equivalentDomains", {
    deserializer: (value) => value !== null && value !== void 0 ? value : null,
    clearOn: ["logout"],
});
const bw_DEFAULT_URI_MATCH_STRATEGY = new bw_UserKeyDefinition(bw_DOMAIN_SETTINGS_DISK, "defaultUriMatchStrategy", {
    deserializer: (value) => value !== null && value !== void 0 ? value : bw_UriMatchStrategy.Domain,
    clearOn: [],
});
/**
 * The Domain Settings service; provides client settings state for "active client view" URI concerns
 */
class bw_DomainSettingsService {
}
class bw_DefaultDomainSettingsService {
    constructor(stateProvider, configService) {
        this.stateProvider = stateProvider;
        this.configService = configService;
        this.showFaviconsState = this.stateProvider.getGlobal(bw_SHOW_FAVICONS);
        this.showFavicons$ = this.showFaviconsState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : true));
        this.neverDomainsState = this.stateProvider.getGlobal(bw_NEVER_DOMAINS);
        this.neverDomains$ = this.neverDomainsState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : null));
        // Needs to be global to prevent pre-login injections
        this.blockedInteractionsUrisState = this.stateProvider.getGlobal(bw_BLOCKED_INTERACTIONS_URIS);
        this.blockedInteractionsUris$ = this.configService
            .getFeatureFlag$(bw_feature_flag_enum_FeatureFlag.BlockBrowserInjectionsByDomain)
            .pipe((0,bw_external_rxjs_namespaceObject.switchMap)((featureIsEnabled) => featureIsEnabled ? this.blockedInteractionsUrisState.state$ : (0,bw_external_rxjs_namespaceObject.of)({})), (0,bw_external_rxjs_namespaceObject.map)((disabledUris) => (Object.keys(disabledUris).length ? disabledUris : {})));
        this.equivalentDomainsState = this.stateProvider.getActive(bw_EQUIVALENT_DOMAINS);
        this.equivalentDomains$ = this.equivalentDomainsState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : null));
        this.defaultUriMatchStrategyState = this.stateProvider.getActive(bw_DEFAULT_URI_MATCH_STRATEGY);
        this.defaultUriMatchStrategy$ = this.defaultUriMatchStrategyState.state$.pipe((0,bw_external_rxjs_namespaceObject.map)((x) => x !== null && x !== void 0 ? x : bw_UriMatchStrategy.Domain));
    }
    setShowFavicons(newValue) {
        return bw_domain_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.showFaviconsState.update(() => newValue);
        });
    }
    setNeverDomains(newValue) {
        return bw_domain_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.neverDomainsState.update(() => newValue);
        });
    }
    setBlockedInteractionsUris(newValue) {
        return bw_domain_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.blockedInteractionsUrisState.update(() => newValue);
        });
    }
    setEquivalentDomains(newValue, userId) {
        return bw_domain_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_EQUIVALENT_DOMAINS).update(() => newValue);
        });
    }
    setDefaultUriMatchStrategy(newValue) {
        return bw_domain_settings_service_awaiter(this, void 0, void 0, function* () {
            yield this.defaultUriMatchStrategyState.update(() => newValue);
        });
    }
    getUrlEquivalentDomains(url) {
        const domains$ = this.equivalentDomains$.pipe((0,bw_external_rxjs_namespaceObject.map)((equivalentDomains) => {
            const domain = bw_utils_Utils.getDomain(url);
            if (domain == null || equivalentDomains == null) {
                return new Set();
            }
            const equivalents = equivalentDomains.filter((ed) => ed.includes(domain)).flat();
            return new Set(equivalents);
        }));
        return domains$;
    }
}

;// ../../libs/common/src/billing/services/account/billing-account-profile-state.service.ts
var bw_billing_account_profile_state_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


const bw_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION = new bw_UserKeyDefinition(bw_BILLING_DISK, "accountProfile", {
    deserializer: (billingAccountProfile) => billingAccountProfile,
    clearOn: ["logout"],
});
class bw_DefaultBillingAccountProfileStateService {
    constructor(stateProvider, platformUtilsService, apiService) {
        this.stateProvider = stateProvider;
        this.platformUtilsService = platformUtilsService;
        this.apiService = apiService;
    }
    hasPremiumFromAnyOrganization$(userId) {
        return this.stateProvider
            .getUser(userId, bw_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((profile) => !!(profile === null || profile === void 0 ? void 0 : profile.hasPremiumFromAnyOrganization)));
    }
    hasPremiumPersonally$(userId) {
        return this.stateProvider
            .getUser(userId, bw_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((profile) => !!(profile === null || profile === void 0 ? void 0 : profile.hasPremiumPersonally)));
    }
    hasPremiumFromAnySource$(userId) {
        return this.stateProvider
            .getUser(userId, bw_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((profile) => (profile === null || profile === void 0 ? void 0 : profile.hasPremiumFromAnyOrganization) === true ||
            (profile === null || profile === void 0 ? void 0 : profile.hasPremiumPersonally) === true));
    }
    setHasPremium(hasPremiumPersonally, hasPremiumFromAnyOrganization, userId) {
        return bw_billing_account_profile_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION).update((_) => {
                return {
                    hasPremiumPersonally: hasPremiumPersonally,
                    hasPremiumFromAnyOrganization: hasPremiumFromAnyOrganization,
                };
            });
        });
    }
    canViewSubscription$(userId) {
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.hasPremiumPersonally$(userId),
            this.hasPremiumFromAnyOrganization$(userId),
        ]).pipe((0,bw_external_rxjs_namespaceObject.concatMap)((_a) => bw_billing_account_profile_state_service_awaiter(this, [_a], void 0, function* ([hasPremiumPersonally, hasPremiumFromOrg]) {
            const isCloud = !this.platformUtilsService.isSelfHost();
            let billing = null;
            if (isCloud) {
                billing = yield this.apiService.getUserBillingHistory();
            }
            const cloudAndBillingHistory = isCloud && !(billing === null || billing === void 0 ? void 0 : billing.hasNoHistory);
            return hasPremiumPersonally || !hasPremiumFromOrg || cloudAndBillingHistory;
        })));
    }
}

;// ../../libs/common/src/platform/models/domain/encrypted-object.ts
class bw_EncryptedObject {
}

;// ../../libs/common/src/key-management/crypto/services/encrypt.service.implementation.ts
var bw_encrypt_service_implementation_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





class bw_EncryptServiceImplementation {
    constructor(cryptoFunctionService, logService, logMacFailures) {
        this.cryptoFunctionService = cryptoFunctionService;
        this.logService = logService;
        this.logMacFailures = logMacFailures;
    }
    encrypt(plainValue, key) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                throw new Error("No encryption key provided.");
            }
            if (plainValue == null) {
                return Promise.resolve(null);
            }
            let plainBuf;
            if (typeof plainValue === "string") {
                plainBuf = bw_utils_Utils.fromUtf8ToArray(plainValue);
            }
            else {
                plainBuf = plainValue;
            }
            const encObj = yield this.aesEncrypt(plainBuf, key);
            const iv = bw_utils_Utils.fromBufferToB64(encObj.iv);
            const data = bw_utils_Utils.fromBufferToB64(encObj.data);
            const mac = encObj.mac != null ? bw_utils_Utils.fromBufferToB64(encObj.mac) : null;
            return new bw_enc_string_EncString(encObj.key.encType, data, iv, mac);
        });
    }
    encryptToBytes(plainValue, key) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                throw new Error("No encryption key provided.");
            }
            const encValue = yield this.aesEncrypt(plainValue, key);
            let macLen = 0;
            if (encValue.mac != null) {
                macLen = encValue.mac.byteLength;
            }
            const encBytes = new Uint8Array(1 + encValue.iv.byteLength + macLen + encValue.data.byteLength);
            encBytes.set([encValue.key.encType]);
            encBytes.set(new Uint8Array(encValue.iv), 1);
            if (encValue.mac != null) {
                encBytes.set(new Uint8Array(encValue.mac), 1 + encValue.iv.byteLength);
            }
            encBytes.set(new Uint8Array(encValue.data), 1 + encValue.iv.byteLength + macLen);
            return new bw_EncArrayBuffer(encBytes);
        });
    }
    decryptToUtf8(encString_1, key_1) {
        return bw_encrypt_service_implementation_awaiter(this, arguments, void 0, function* (encString, key, decryptContext = "no context") {
            if (key == null) {
                throw new Error("No key provided for decryption.");
            }
            // DO NOT REMOVE OR MOVE. This prevents downgrade to mac-less CBC, which would compromise integrity and confidentiality.
            if (key.macKey != null && (encString === null || encString === void 0 ? void 0 : encString.mac) == null) {
                this.logService.error("[Encrypt service] Key has mac key but payload is missing mac bytes. Key type " +
                    bw_encryptionTypeToString(key.encType) +
                    "Payload type " +
                    bw_encryptionTypeToString(encString.encryptionType), "Decrypt context: " + decryptContext);
                return null;
            }
            if (key.encType !== encString.encryptionType) {
                this.logService.error("[Encrypt service] Key encryption type does not match payload encryption type. Key type " +
                    bw_encryptionTypeToString(key.encType) +
                    "Payload type " +
                    bw_encryptionTypeToString(encString.encryptionType), "Decrypt context: " + decryptContext);
                return null;
            }
            const fastParams = this.cryptoFunctionService.aesDecryptFastParameters(encString.data, encString.iv, encString.mac, key);
            if (fastParams.macKey != null && fastParams.mac != null) {
                const computedMac = yield this.cryptoFunctionService.hmacFast(fastParams.macData, fastParams.macKey, "sha256");
                const macsEqual = yield this.cryptoFunctionService.compareFast(fastParams.mac, computedMac);
                if (!macsEqual) {
                    this.logMacFailed("[Encrypt service] decryptToUtf8 MAC comparison failed. Key or payload has changed. Key type " +
                        bw_encryptionTypeToString(key.encType) +
                        "Payload type " +
                        bw_encryptionTypeToString(encString.encryptionType) +
                        " Decrypt context: " +
                        decryptContext);
                    return null;
                }
            }
            return yield this.cryptoFunctionService.aesDecryptFast({ mode: "cbc", parameters: fastParams });
        });
    }
    decryptToBytes(encThing_1, key_1) {
        return bw_encrypt_service_implementation_awaiter(this, arguments, void 0, function* (encThing, key, decryptContext = "no context") {
            if (key == null) {
                throw new Error("No encryption key provided.");
            }
            if (encThing == null) {
                throw new Error("Nothing provided for decryption.");
            }
            // DO NOT REMOVE OR MOVE. This prevents downgrade to mac-less CBC, which would compromise integrity and confidentiality.
            if (key.macKey != null && encThing.macBytes == null) {
                this.logService.error("[Encrypt service] Key has mac key but payload is missing mac bytes. Key type " +
                    bw_encryptionTypeToString(key.encType) +
                    " Payload type " +
                    bw_encryptionTypeToString(encThing.encryptionType) +
                    " Decrypt context: " +
                    decryptContext);
                return null;
            }
            if (key.encType !== encThing.encryptionType) {
                this.logService.error("[Encrypt service] Key encryption type does not match payload encryption type. Key type " +
                    bw_encryptionTypeToString(key.encType) +
                    " Payload type " +
                    bw_encryptionTypeToString(encThing.encryptionType) +
                    " Decrypt context: " +
                    decryptContext);
                return null;
            }
            if (key.macKey != null && encThing.macBytes != null) {
                const macData = new Uint8Array(encThing.ivBytes.byteLength + encThing.dataBytes.byteLength);
                macData.set(new Uint8Array(encThing.ivBytes), 0);
                macData.set(new Uint8Array(encThing.dataBytes), encThing.ivBytes.byteLength);
                const computedMac = yield this.cryptoFunctionService.hmac(macData, key.macKey, "sha256");
                if (computedMac === null) {
                    this.logMacFailed("[Encrypt service#decryptToBytes] Failed to compute MAC." +
                        " Key type " +
                        bw_encryptionTypeToString(key.encType) +
                        " Payload type " +
                        bw_encryptionTypeToString(encThing.encryptionType) +
                        " Decrypt context: " +
                        decryptContext);
                    return null;
                }
                const macsMatch = yield this.cryptoFunctionService.compare(encThing.macBytes, computedMac);
                if (!macsMatch) {
                    this.logMacFailed("[Encrypt service#decryptToBytes]: MAC comparison failed. Key or payload has changed." +
                        " Key type " +
                        bw_encryptionTypeToString(key.encType) +
                        " Payload type " +
                        bw_encryptionTypeToString(encThing.encryptionType) +
                        " Decrypt context: " +
                        decryptContext);
                    return null;
                }
            }
            const result = yield this.cryptoFunctionService.aesDecrypt(encThing.dataBytes, encThing.ivBytes, key.encKey, "cbc");
            return result !== null && result !== void 0 ? result : null;
        });
    }
    rsaEncrypt(data, publicKey) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (data == null) {
                throw new Error("No data provided for encryption.");
            }
            if (publicKey == null) {
                throw new Error("No public key provided for encryption.");
            }
            const encrypted = yield this.cryptoFunctionService.rsaEncrypt(data, publicKey, "sha1");
            return new bw_enc_string_EncString(bw_EncryptionType.Rsa2048_OaepSha1_B64, bw_utils_Utils.fromBufferToB64(encrypted));
        });
    }
    rsaDecrypt(data, privateKey) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (data == null) {
                throw new Error("[Encrypt service] rsaDecrypt: No data provided for decryption.");
            }
            let algorithm;
            switch (data.encryptionType) {
                case bw_EncryptionType.Rsa2048_OaepSha1_B64:
                case bw_EncryptionType.Rsa2048_OaepSha1_HmacSha256_B64:
                    algorithm = "sha1";
                    break;
                case bw_EncryptionType.Rsa2048_OaepSha256_B64:
                case bw_EncryptionType.Rsa2048_OaepSha256_HmacSha256_B64:
                    algorithm = "sha256";
                    break;
                default:
                    throw new Error("Invalid encryption type.");
            }
            if (privateKey == null) {
                throw new Error("[Encrypt service] rsaDecrypt: No private key provided for decryption.");
            }
            return this.cryptoFunctionService.rsaDecrypt(data.dataBytes, privateKey, algorithm);
        });
    }
    /**
     * @deprecated Replaced by BulkEncryptService (PM-4154)
     */
    decryptItems(items, key) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (items == null || items.length < 1) {
                return [];
            }
            // don't use promise.all because this task is not io bound
            const results = [];
            for (let i = 0; i < items.length; i++) {
                results.push(yield items[i].decrypt(key));
            }
            return results;
        });
    }
    hash(value, algorithm) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            const hashArray = yield this.cryptoFunctionService.hash(value, algorithm);
            return bw_utils_Utils.fromBufferToB64(hashArray);
        });
    }
    aesEncrypt(data, key) {
        return bw_encrypt_service_implementation_awaiter(this, void 0, void 0, function* () {
            const obj = new bw_EncryptedObject();
            obj.key = key;
            obj.iv = yield this.cryptoFunctionService.randomBytes(16);
            obj.data = yield this.cryptoFunctionService.aesEncrypt(data, obj.iv, obj.key.encKey);
            if (obj.key.macKey != null) {
                const macData = new Uint8Array(obj.iv.byteLength + obj.data.byteLength);
                macData.set(new Uint8Array(obj.iv), 0);
                macData.set(new Uint8Array(obj.data), obj.iv.byteLength);
                obj.mac = yield this.cryptoFunctionService.hmac(macData, obj.key.macKey, "sha256");
            }
            return obj;
        });
    }
    logMacFailed(msg) {
        if (this.logMacFailures) {
            this.logService.error(msg);
        }
    }
}

;// ../../libs/common/src/key-management/crypto/services/fallback-bulk-encrypt.service.ts
var bw_fallback_bulk_encrypt_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
/**
 * @deprecated For the feature flag from PM-4154, remove once feature is rolled out
 */
class bw_FallbackBulkEncryptService {
    constructor(encryptService) {
        this.encryptService = encryptService;
    }
    /**
     * Decrypts items using a web worker if the environment supports it.
     * Will fall back to the main thread if the window object is not available.
     */
    decryptItems(items, key) {
        return bw_fallback_bulk_encrypt_service_awaiter(this, void 0, void 0, function* () {
            if (this.featureFlagEncryptService != null) {
                return yield this.featureFlagEncryptService.decryptItems(items, key);
            }
            else {
                return yield this.encryptService.decryptItems(items, key);
            }
        });
    }
    setFeatureFlagEncryptService(featureFlagEncryptService) {
        return bw_fallback_bulk_encrypt_service_awaiter(this, void 0, void 0, function* () {
            this.featureFlagEncryptService = featureFlagEncryptService;
        });
    }
}

;// ../../libs/common/src/auth/models/request/update-devices-trust.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_UpdateDevicesTrustRequest extends bw_SecretVerificationRequest {
}
class bw_DeviceKeysUpdateRequest {
}
class bw_OtherDeviceKeysUpdateRequest extends (/* unused pure expression or super */ null && (bw_DeviceKeysUpdateRequest)) {
}

;// ../../libs/common/src/key-management/device-trust/services/device-trust.service.implementation.ts
var bw_device_trust_service_implementation_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







/** Uses disk storage so that the device key can persist after log out and tab removal. */
const bw_DEVICE_KEY = new bw_UserKeyDefinition(bw_DEVICE_TRUST_DISK_LOCAL, "deviceKey", {
    deserializer: (deviceKey) => deviceKey ? bw_SymmetricCryptoKey.fromJSON(deviceKey) : null,
    clearOn: [], // Device key is needed to log back into device, so we can't clear it automatically during lock or logout
    cleanupDelayMs: 0,
    debug: {
        enableRetrievalLogging: true,
        enableUpdateLogging: true,
    },
});
/** Uses disk storage so that the shouldTrustDevice bool can persist across login. */
const bw_SHOULD_TRUST_DEVICE = new bw_UserKeyDefinition(bw_DEVICE_TRUST_DISK_LOCAL, "shouldTrustDevice", {
    deserializer: (shouldTrustDevice) => shouldTrustDevice,
    clearOn: [], // Need to preserve the user setting, so we can't clear it automatically during lock or logout
});
class bw_DeviceTrustService {
    constructor(keyGenerationService, cryptoFunctionService, keyService, encryptService, appIdService, devicesApiService, i18nService, platformUtilsService, stateProvider, secureStorageService, userDecryptionOptionsService, logService, configService) {
        this.keyGenerationService = keyGenerationService;
        this.cryptoFunctionService = cryptoFunctionService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.appIdService = appIdService;
        this.devicesApiService = devicesApiService;
        this.i18nService = i18nService;
        this.platformUtilsService = platformUtilsService;
        this.stateProvider = stateProvider;
        this.secureStorageService = secureStorageService;
        this.userDecryptionOptionsService = userDecryptionOptionsService;
        this.logService = logService;
        this.configService = configService;
        this.platformSupportsSecureStorage = this.platformUtilsService.supportsSecureStorage();
        this.deviceKeySecureStorageKey = "_deviceKey";
        // Observable emission is used to trigger a toast in consuming components
        this.deviceTrustedSubject = new bw_external_rxjs_namespaceObject.Subject();
        this.deviceTrusted$ = this.deviceTrustedSubject.asObservable();
        this.supportsDeviceTrust$ = this.userDecryptionOptionsService.userDecryptionOptions$.pipe((0,bw_external_rxjs_namespaceObject.map)((options) => {
            var _a;
            return (_a = (options === null || options === void 0 ? void 0 : options.trustedDeviceOption) != null) !== null && _a !== void 0 ? _a : false;
        }));
    }
    supportsDeviceTrustByUserId$(userId) {
        return this.userDecryptionOptionsService.userDecryptionOptionsById$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((options) => {
            var _a;
            return (_a = (options === null || options === void 0 ? void 0 : options.trustedDeviceOption) != null) !== null && _a !== void 0 ? _a : false;
        }));
    }
    /**
     * @description Retrieves the users choice to trust the device which can only happen after decryption
     * Note: this value should only be used once and then reset
     */
    getShouldTrustDevice(userId) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot get should trust device.");
            }
            const shouldTrustDevice = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_SHOULD_TRUST_DEVICE, userId));
            return shouldTrustDevice;
        });
    }
    setShouldTrustDevice(userId, value) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot set should trust device.");
            }
            yield this.stateProvider.setUserState(bw_SHOULD_TRUST_DEVICE, value, userId);
        });
    }
    trustDeviceIfRequired(userId) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot trust device if required.");
            }
            const shouldTrustDevice = yield this.getShouldTrustDevice(userId);
            if (shouldTrustDevice) {
                yield this.trustDevice(userId);
                // reset the trust choice
                yield this.setShouldTrustDevice(userId, null);
            }
        });
    }
    trustDevice(userId) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot trust device.");
            }
            // Attempt to get user key
            const userKey = yield this.keyService.getUserKey(userId);
            // If user key is not found, throw error
            if (!userKey) {
                throw new Error("User symmetric key not found");
            }
            // Generate deviceKey
            const deviceKey = yield this.makeDeviceKey();
            // Generate asymmetric RSA key pair: devicePrivateKey, devicePublicKey
            const [devicePublicKey, devicePrivateKey] = yield this.cryptoFunctionService.rsaGenerateKeyPair(2048);
            const [devicePublicKeyEncryptedUserKey, userKeyEncryptedDevicePublicKey, deviceKeyEncryptedDevicePrivateKey,] = yield Promise.all([
                // Encrypt user key with the DevicePublicKey
                this.encryptService.rsaEncrypt(userKey.key, devicePublicKey),
                // Encrypt devicePublicKey with user key
                this.encryptService.encrypt(devicePublicKey, userKey),
                // Encrypt devicePrivateKey with deviceKey
                this.encryptService.encrypt(devicePrivateKey, deviceKey),
            ]);
            // Send encrypted keys to server
            const deviceIdentifier = yield this.appIdService.getAppId();
            const deviceResponse = yield this.devicesApiService.updateTrustedDeviceKeys(deviceIdentifier, devicePublicKeyEncryptedUserKey.encryptedString, userKeyEncryptedDevicePublicKey.encryptedString, deviceKeyEncryptedDevicePrivateKey.encryptedString);
            // store device key in local/secure storage if enc keys posted to server successfully
            yield this.setDeviceKey(userId, deviceKey);
            // This emission will be picked up by consuming components to handle displaying a toast to the user
            this.deviceTrustedSubject.next();
            return deviceResponse;
        });
    }
    rotateDevicesTrust(userId, newUserKey, masterPasswordHash) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            this.logService.info("[Device trust rotation] Rotating device trust...");
            if (!userId) {
                throw new Error("UserId is required. Cannot rotate device's trust.");
            }
            const currentDeviceKey = yield this.getDeviceKey(userId);
            if (currentDeviceKey == null) {
                // If the current device doesn't have a device key available to it, then we can't
                // rotate any trust at all, so early return.
                this.logService.info("[Device trust rotation] No device key available to rotate trust!");
                return;
            }
            // At this point of rotating their keys, they should still have their old user key in state
            const oldUserKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.userKey$(userId));
            if (oldUserKey == newUserKey) {
                this.logService.info("[Device trust rotation] Old user key is the same as the new user key.");
            }
            const deviceIdentifier = yield this.appIdService.getAppId();
            const secretVerificationRequest = new bw_SecretVerificationRequest();
            secretVerificationRequest.masterPasswordHash = masterPasswordHash;
            // Get the keys that are used in rotating a devices keys from the server
            const currentDeviceKeys = yield this.devicesApiService.getDeviceKeys(deviceIdentifier, secretVerificationRequest);
            // Decrypt the existing device public key with the old user key
            const decryptedDevicePublicKey = yield this.encryptService.decryptToBytes(currentDeviceKeys.encryptedPublicKey, oldUserKey);
            // Encrypt the brand new user key with the now-decrypted public key for the device
            const encryptedNewUserKey = yield this.encryptService.rsaEncrypt(newUserKey.key, decryptedDevicePublicKey);
            // Re-encrypt the device public key with the new user key
            const encryptedDevicePublicKey = yield this.encryptService.encrypt(decryptedDevicePublicKey, newUserKey);
            const currentDeviceUpdateRequest = new bw_DeviceKeysUpdateRequest();
            currentDeviceUpdateRequest.encryptedUserKey = encryptedNewUserKey.encryptedString;
            currentDeviceUpdateRequest.encryptedPublicKey = encryptedDevicePublicKey.encryptedString;
            // TODO: For device management, allow this method to take an array of device ids that can be looped over and individually rotated
            // then it can be added to trustRequest.otherDevices.
            const trustRequest = new bw_UpdateDevicesTrustRequest();
            trustRequest.masterPasswordHash = masterPasswordHash;
            trustRequest.currentDevice = currentDeviceUpdateRequest;
            trustRequest.otherDevices = [];
            this.logService.info("[Device trust rotation] Posting device trust update with current device:", deviceIdentifier);
            yield this.devicesApiService.updateTrust(trustRequest, deviceIdentifier);
            this.logService.info("[Device trust rotation] Device trust update posted successfully.");
        });
    }
    getDeviceKey(userId) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot get device key.");
            }
            try {
                if (this.platformSupportsSecureStorage) {
                    const deviceKeyB64 = yield this.secureStorageService.get(`${userId}${this.deviceKeySecureStorageKey}`, this.getSecureStorageOptions(userId));
                    const deviceKey = bw_SymmetricCryptoKey.fromJSON(deviceKeyB64);
                    return deviceKey;
                }
                const deviceKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_DEVICE_KEY, userId));
                return deviceKey;
            }
            catch (e) {
                this.logService.error("Failed to get device key", e);
            }
        });
    }
    setDeviceKey(userId, deviceKey) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot set device key.");
            }
            try {
                if (this.platformSupportsSecureStorage) {
                    yield this.secureStorageService.save(`${userId}${this.deviceKeySecureStorageKey}`, deviceKey, this.getSecureStorageOptions(userId));
                    return;
                }
                yield this.stateProvider.setUserState(bw_DEVICE_KEY, deviceKey === null || deviceKey === void 0 ? void 0 : deviceKey.toJSON(), userId);
            }
            catch (e) {
                this.logService.error("Failed to set device key", e);
            }
        });
    }
    makeDeviceKey() {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            // Create 512-bit device key
            const deviceKey = (yield this.keyGenerationService.createKey(512));
            return deviceKey;
        });
    }
    decryptUserKeyWithDeviceKey(userId, encryptedDevicePrivateKey, encryptedUserKey, deviceKey) {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                throw new Error("UserId is required. Cannot decrypt user key with device key.");
            }
            if (!encryptedDevicePrivateKey) {
                throw new Error("Encrypted device private key is required. Cannot decrypt user key with device key.");
            }
            if (!encryptedUserKey) {
                throw new Error("Encrypted user key is required. Cannot decrypt user key with device key.");
            }
            if (!deviceKey) {
                // User doesn't have a device key anymore so device is untrusted
                return null;
            }
            try {
                // attempt to decrypt encryptedDevicePrivateKey with device key
                const devicePrivateKey = yield this.encryptService.decryptToBytes(encryptedDevicePrivateKey, deviceKey);
                // Attempt to decrypt encryptedUserDataKey with devicePrivateKey
                const userKey = yield this.encryptService.rsaDecrypt(new bw_enc_string_EncString(encryptedUserKey.encryptedString), devicePrivateKey);
                return new bw_SymmetricCryptoKey(userKey);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                // If either decryption effort fails, we want to remove the device key
                this.logService.error("Failed to decrypt using device key. Removing device key.");
                yield this.setDeviceKey(userId, null);
                return null;
            }
        });
    }
    recordDeviceTrustLoss() {
        return bw_device_trust_service_implementation_awaiter(this, void 0, void 0, function* () {
            const deviceIdentifier = yield this.appIdService.getAppId();
            yield this.devicesApiService.postDeviceTrustLoss(deviceIdentifier);
        });
    }
    getSecureStorageOptions(userId) {
        return {
            storageLocation: bw_StorageLocation.Disk,
            useSecureStorage: true,
            userId: userId,
        };
    }
}

;// ../../libs/common/src/key-management/key-connector/models/key-connector-user-key.request.ts
class bw_KeyConnectorUserKeyRequest {
    constructor(key) {
        this.key = key;
    }
}

;// ../../libs/common/src/key-management/key-connector/models/set-key-connector-key.request.ts

class bw_SetKeyConnectorKeyRequest {
    constructor(key, kdfConfig, orgIdentifier, keys) {
        this.key = key;
        this.kdf = kdfConfig.kdfType;
        this.kdfIterations = kdfConfig.iterations;
        if (kdfConfig.kdfType === bw_KdfType.Argon2id) {
            this.kdfMemory = kdfConfig.memory;
            this.kdfParallelism = kdfConfig.parallelism;
        }
        this.orgIdentifier = orgIdentifier;
        this.keys = keys;
    }
}

;// ../../libs/common/src/key-management/key-connector/services/key-connector.service.ts
var bw_key_connector_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore









const bw_USES_KEY_CONNECTOR = new bw_UserKeyDefinition(bw_KEY_CONNECTOR_DISK, "usesKeyConnector", {
    deserializer: (usesKeyConnector) => usesKeyConnector,
    clearOn: ["logout"],
});
const bw_CONVERT_ACCOUNT_TO_KEY_CONNECTOR = new bw_UserKeyDefinition(bw_KEY_CONNECTOR_DISK, "convertAccountToKeyConnector", {
    deserializer: (convertAccountToKeyConnector) => convertAccountToKeyConnector,
    clearOn: ["logout"],
});
class bw_KeyConnectorService {
    constructor(accountService, masterPasswordService, keyService, apiService, tokenService, logService, organizationService, keyGenerationService, logoutCallback, stateProvider) {
        this.accountService = accountService;
        this.masterPasswordService = masterPasswordService;
        this.keyService = keyService;
        this.apiService = apiService;
        this.tokenService = tokenService;
        this.logService = logService;
        this.organizationService = organizationService;
        this.keyGenerationService = keyGenerationService;
        this.logoutCallback = logoutCallback;
        this.stateProvider = stateProvider;
        this.usesKeyConnectorState = this.stateProvider.getActive(bw_USES_KEY_CONNECTOR);
        this.convertAccountToKeyConnectorState = this.stateProvider.getActive(bw_CONVERT_ACCOUNT_TO_KEY_CONNECTOR);
    }
    setUsesKeyConnector(usesKeyConnector, userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_USES_KEY_CONNECTOR).update(() => usesKeyConnector);
        });
    }
    getUsesKeyConnector(userId) {
        return (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUserState$(bw_USES_KEY_CONNECTOR, userId));
    }
    userNeedsMigration(userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            const loggedInUsingSso = yield this.tokenService.getIsExternal(userId);
            const requiredByOrganization = (yield this.getManagingOrganization(userId)) != null;
            const userIsNotUsingKeyConnector = !(yield this.getUsesKeyConnector(userId));
            return loggedInUsingSso && requiredByOrganization && userIsNotUsingKeyConnector;
        });
    }
    migrateUser(userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            userId !== null && userId !== void 0 ? userId : (userId = (_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$))) === null || _a === void 0 ? void 0 : _a.id);
            const organization = yield this.getManagingOrganization(userId);
            const masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterPasswordService.masterKey$(userId));
            const keyConnectorRequest = new bw_KeyConnectorUserKeyRequest(masterKey.encKeyB64);
            try {
                yield this.apiService.postUserKeyToKeyConnector(organization.keyConnectorUrl, keyConnectorRequest);
            }
            catch (e) {
                this.handleKeyConnectorError(e);
            }
            yield this.apiService.postConvertToKeyConnector();
        });
    }
    // TODO: UserKey should be renamed to MasterKey and typed accordingly
    setMasterKeyFromUrl(url, userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            try {
                const masterKeyResponse = yield this.apiService.getMasterKeyFromKeyConnector(url);
                const keyArr = bw_utils_Utils.fromB64ToArray(masterKeyResponse.key);
                const masterKey = new bw_SymmetricCryptoKey(keyArr);
                yield this.masterPasswordService.setMasterKey(masterKey, userId);
            }
            catch (e) {
                this.handleKeyConnectorError(e);
            }
        });
    }
    getManagingOrganization(userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            const orgs = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.organizationService.organizations$(userId));
            return orgs.find((o) => o.keyConnectorEnabled &&
                o.type !== bw_OrganizationUserType.Admin &&
                o.type !== bw_OrganizationUserType.Owner &&
                !o.isProviderUser);
        });
    }
    convertNewSsoUserToKeyConnector(tokenResponse, orgId, userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            // TODO: Remove after tokenResponse.keyConnectorUrl is deprecated in 2023.10 release (https://bitwarden.atlassian.net/browse/PM-3537)
            const { kdf, kdfIterations, kdfMemory, kdfParallelism, keyConnectorUrl: legacyKeyConnectorUrl, userDecryptionOptions, } = tokenResponse;
            const password = yield this.keyGenerationService.createKey(512);
            const kdfConfig = kdf === bw_KdfType.PBKDF2_SHA256
                ? new bw_PBKDF2KdfConfig(kdfIterations)
                : new bw_Argon2KdfConfig(kdfIterations, kdfMemory, kdfParallelism);
            const masterKey = yield this.keyService.makeMasterKey(password.keyB64, yield this.tokenService.getEmail(), kdfConfig);
            const keyConnectorRequest = new bw_KeyConnectorUserKeyRequest(masterKey.encKeyB64);
            yield this.masterPasswordService.setMasterKey(masterKey, userId);
            const userKey = yield this.keyService.makeUserKey(masterKey);
            yield this.keyService.setUserKey(userKey[0], userId);
            yield this.keyService.setMasterKeyEncryptedUserKey(userKey[1].encryptedString, userId);
            const [pubKey, privKey] = yield this.keyService.makeKeyPair(userKey[0]);
            try {
                const keyConnectorUrl = legacyKeyConnectorUrl !== null && legacyKeyConnectorUrl !== void 0 ? legacyKeyConnectorUrl : (_a = userDecryptionOptions === null || userDecryptionOptions === void 0 ? void 0 : userDecryptionOptions.keyConnectorOption) === null || _a === void 0 ? void 0 : _a.keyConnectorUrl;
                yield this.apiService.postUserKeyToKeyConnector(keyConnectorUrl, keyConnectorRequest);
            }
            catch (e) {
                this.handleKeyConnectorError(e);
            }
            const keys = new bw_KeysRequest(pubKey, privKey.encryptedString);
            const setPasswordRequest = new bw_SetKeyConnectorKeyRequest(userKey[1].encryptedString, kdfConfig, orgId, keys);
            yield this.apiService.postSetKeyConnectorKey(setPasswordRequest);
        });
    }
    setConvertAccountRequired(status, userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_CONVERT_ACCOUNT_TO_KEY_CONNECTOR, status, userId);
        });
    }
    getConvertAccountRequired() {
        return (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.convertAccountToKeyConnectorState.state$);
    }
    removeConvertAccountRequired(userId) {
        return bw_key_connector_service_awaiter(this, void 0, void 0, function* () {
            yield this.setConvertAccountRequired(null, userId);
        });
    }
    handleKeyConnectorError(e) {
        this.logService.error(e);
        if (this.logoutCallback != null) {
            // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
            // eslint-disable-next-line @typescript-eslint/no-floating-promises
            this.logoutCallback("keyConnectorError");
        }
        throw new Error("Key Connector error");
    }
}

;// ../../libs/common/src/key-management/master-password/services/master-password.service.ts
var bw_master_password_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






/** Memory since master key shouldn't be available on lock */
const bw_MASTER_KEY = new bw_UserKeyDefinition(bw_MASTER_PASSWORD_MEMORY, "masterKey", {
    deserializer: (masterKey) => bw_SymmetricCryptoKey.fromJSON(masterKey),
    clearOn: ["lock", "logout"],
});
/** Disk since master key hash is used for unlock */
const bw_MASTER_KEY_HASH = new bw_UserKeyDefinition(bw_MASTER_PASSWORD_DISK, "masterKeyHash", {
    deserializer: (masterKeyHash) => masterKeyHash,
    clearOn: ["logout"],
});
/** Disk to persist through lock */
const bw_MASTER_KEY_ENCRYPTED_USER_KEY = new bw_UserKeyDefinition(bw_MASTER_PASSWORD_DISK, "masterKeyEncryptedUserKey", {
    deserializer: (key) => key,
    clearOn: ["logout"],
});
/** Disk to persist through lock and account switches */
const bw_FORCE_SET_PASSWORD_REASON = new bw_UserKeyDefinition(bw_MASTER_PASSWORD_DISK, "forceSetPasswordReason", {
    deserializer: (reason) => reason,
    clearOn: ["logout"],
});
class bw_MasterPasswordService {
    constructor(stateProvider, stateService, keyGenerationService, encryptService, logService) {
        this.stateProvider = stateProvider;
        this.stateService = stateService;
        this.keyGenerationService = keyGenerationService;
        this.encryptService = encryptService;
        this.logService = logService;
    }
    masterKey$(userId) {
        if (userId == null) {
            throw new Error("User ID is required.");
        }
        return this.stateProvider.getUser(userId, bw_MASTER_KEY).state$;
    }
    masterKeyHash$(userId) {
        if (userId == null) {
            throw new Error("User ID is required.");
        }
        return this.stateProvider.getUser(userId, bw_MASTER_KEY_HASH).state$;
    }
    forceSetPasswordReason$(userId) {
        if (userId == null) {
            throw new Error("User ID is required.");
        }
        return this.stateProvider
            .getUser(userId, bw_FORCE_SET_PASSWORD_REASON)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((reason) => reason !== null && reason !== void 0 ? reason : bw_ForceSetPasswordReason.None));
    }
    // TODO: Remove this method and decrypt directly in the service instead
    getMasterKeyEncryptedUserKey(userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            const key = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_MASTER_KEY_ENCRYPTED_USER_KEY).state$);
            return bw_enc_string_EncString.fromJSON(key);
        });
    }
    setMasterKey(masterKey, userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (masterKey == null) {
                throw new Error("Master key is required.");
            }
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.stateProvider.getUser(userId, bw_MASTER_KEY).update((_) => masterKey);
        });
    }
    clearMasterKey(userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.stateProvider.getUser(userId, bw_MASTER_KEY).update((_) => null);
        });
    }
    setMasterKeyHash(masterKeyHash, userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (masterKeyHash == null) {
                throw new Error("Master key hash is required.");
            }
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.stateProvider.getUser(userId, bw_MASTER_KEY_HASH).update((_) => masterKeyHash);
        });
    }
    clearMasterKeyHash(userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.stateProvider.getUser(userId, bw_MASTER_KEY_HASH).update((_) => null);
        });
    }
    setMasterKeyEncryptedUserKey(encryptedKey, userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (encryptedKey == null) {
                throw new Error("Encrypted Key is required.");
            }
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.stateProvider
                .getUser(userId, bw_MASTER_KEY_ENCRYPTED_USER_KEY)
                .update((_) => encryptedKey.toJSON());
        });
    }
    setForceSetPasswordReason(reason, userId) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            if (reason == null) {
                throw new Error("Reason is required.");
            }
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.stateProvider.getUser(userId, bw_FORCE_SET_PASSWORD_REASON).update((_) => reason);
        });
    }
    decryptUserKeyWithMasterKey(masterKey, userId, userKey) {
        return bw_master_password_service_awaiter(this, void 0, void 0, function* () {
            userKey !== null && userKey !== void 0 ? userKey : (userKey = yield this.getMasterKeyEncryptedUserKey(userId));
            masterKey !== null && masterKey !== void 0 ? masterKey : (masterKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.masterKey$(userId)));
            if (masterKey == null) {
                throw new Error("No master key found.");
            }
            // Try one more way to get the user key if it still wasn't found.
            if (userKey == null) {
                const deprecatedKey = yield this.stateService.getEncryptedCryptoSymmetricKey({
                    userId: userId,
                });
                if (deprecatedKey == null) {
                    throw new Error("No encrypted user key found.");
                }
                userKey = new bw_enc_string_EncString(deprecatedKey);
            }
            let decUserKey;
            if (userKey.encryptionType === bw_EncryptionType.AesCbc256_B64) {
                decUserKey = yield this.encryptService.decryptToBytes(userKey, masterKey, "Content: User Key; Encrypting Key: Master Key");
            }
            else if (userKey.encryptionType === bw_EncryptionType.AesCbc256_HmacSha256_B64) {
                const newKey = yield this.keyGenerationService.stretchKey(masterKey);
                decUserKey = yield this.encryptService.decryptToBytes(userKey, newKey, "Content: User Key; Encrypting Key: Stretched Master Key");
            }
            else {
                throw new Error("Unsupported encryption type.");
            }
            if (decUserKey == null) {
                this.logService.warning("Failed to decrypt user key with master key.");
                return null;
            }
            return new bw_SymmetricCryptoKey(decUserKey);
        });
    }
}

;// ../../libs/common/src/platform/factories/account-factory.ts
class bw_AccountFactory {
    constructor(accountConstructor) {
        this.accountConstructor = accountConstructor;
    }
    create(args) {
        return new this.accountConstructor(args);
    }
}

;// ../../libs/common/src/platform/factories/global-state-factory.ts
class bw_GlobalStateFactory {
    constructor(globalStateConstructor) {
        this.globalStateConstructor = globalStateConstructor;
    }
    create(args) {
        return new this.globalStateConstructor(args);
    }
}

;// ../../libs/common/src/platform/factories/state-factory.ts


class bw_StateFactory {
    constructor(globalStateConstructor, accountConstructor) {
        this.globalStateFactory = new bw_GlobalStateFactory(globalStateConstructor);
        this.accountFactory = new bw_AccountFactory(accountConstructor);
    }
    createGlobal(args) {
        return this.globalStateFactory.create(args);
    }
    createAccount(args) {
        return this.accountFactory.create(args);
    }
}

;// ../../libs/common/src/platform/messaging/message.listener.ts

/**
 * A class that allows for listening to messages coming through the application,
 * allows for listening of all messages or just the messages you care about.
 *
 * @note Consider NOT using messaging at all if you can. State Providers offer an observable stream of
 * data that is persisted. This can serve messages that might have been used to notify of settings changes
 * or vault data changes and those observables should be preferred over messaging.
 */
class bw_MessageListener {
    constructor(messageStream) {
        this.messageStream = messageStream;
        /**
         * A stream of all messages sent through the application. It does not contain type information for the
         * other properties on the messages. You are encouraged to instead subscribe to an individual message
         * through {@link messages$}.
         */
        this.allMessages$ = this.messageStream;
    }
    /**
     * Creates an observable stream filtered to just the command given via the {@link CommandDefinition} and typed
     * to the generic contained in the CommandDefinition. Be careful using this method unless all your messages are being
     * sent through `MessageSender.send`, if that isn't the case you should have lower confidence in the message
     * payload being the expected type.
     *
     * @param commandDefinition The CommandDefinition containing the information about the message type you care about.
     */
    messages$(commandDefinition) {
        return this.allMessages$.pipe((0,bw_external_rxjs_namespaceObject.filter)((msg) => (msg === null || msg === void 0 ? void 0 : msg.command) === commandDefinition.command));
    }
}
/**
 * A helper property for returning a MessageListener that will never emit any messages and will immediately complete.
 */
bw_MessageListener.EMPTY = new bw_MessageListener(bw_external_rxjs_namespaceObject.EMPTY);

;// ../../libs/common/src/platform/messaging/message.sender.ts
class bw_MultiMessageSender {
    constructor(innerMessageSenders) {
        this.innerMessageSenders = innerMessageSenders;
    }
    send(commandDefinition, payload = {}) {
        for (const messageSender of this.innerMessageSenders) {
            messageSender.send(commandDefinition, payload);
        }
    }
}
class bw_MessageSender {
    /**
     * A helper method for combine multiple {@link MessageSender}'s.
     * @param messageSenders The message senders that should be combined.
     * @returns A message sender that will relay all messages to the given message senders.
     */
    static combine(...messageSenders) {
        return new bw_MultiMessageSender(messageSenders);
    }
}
/**
 * A helper property for creating a {@link MessageSender} that sends to nowhere.
 */
bw_MessageSender.EMPTY = new bw_MultiMessageSender([]);

;// ../../libs/common/src/platform/messaging/helpers.ts

const bw_getCommand = (commandDefinition) => {
    if (typeof commandDefinition === "string") {
        return commandDefinition;
    }
    else {
        return commandDefinition.command;
    }
};
const bw_EXTERNAL_SOURCE_TAG = Symbol("externalSource");
const bw_isExternalMessage = (message) => {
    return (message === null || message === void 0 ? void 0 : message[bw_EXTERNAL_SOURCE_TAG]) === true;
};
const bw_tagAsExternal = () => {
    return map((message) => {
        return Object.assign(message, { [bw_EXTERNAL_SOURCE_TAG]: true });
    });
};

;// ../../libs/common/src/platform/messaging/index.ts





;// ../../libs/common/src/platform/models/domain/global-state.ts
class bw_GlobalState {
}

;// ../../libs/common/src/platform/services/app-id.service.ts
var bw_app_id_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_APP_ID_KEY = "global_applicationId_appId";
const bw_ANONYMOUS_APP_ID_KEY = "global_applicationId_appId";
class bw_AppIdService {
    constructor(storageService, logService) {
        this.storageService = storageService;
        this.logService = logService;
    }
    getAppId() {
        return bw_app_id_service_awaiter(this, void 0, void 0, function* () {
            this.logService.info("Retrieving application id");
            return yield this.getEnsuredValue(bw_APP_ID_KEY);
        });
    }
    getAnonymousAppId() {
        return bw_app_id_service_awaiter(this, void 0, void 0, function* () {
            return yield this.getEnsuredValue(bw_ANONYMOUS_APP_ID_KEY);
        });
    }
    getEnsuredValue(key) {
        return bw_app_id_service_awaiter(this, void 0, void 0, function* () {
            let value = yield this.storageService.get(key);
            if (value == null) {
                value = bw_utils_Utils.newGuid();
                yield this.storageService.save(key, value);
            }
            return value;
        });
    }
}

;// ../../libs/common/src/platform/models/domain/server-settings.ts
class bw_ServerSettings {
    constructor(data) {
        var _a;
        this.disableUserRegistration = (_a = data === null || data === void 0 ? void 0 : data.disableUserRegistration) !== null && _a !== void 0 ? _a : false;
    }
}

;// ../../libs/common/src/platform/models/response/server-config.response.ts


class bw_ServerConfigResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.featureStates = {};
        if (response == null) {
            return;
        }
        this.version = this.getResponseProperty("Version");
        this.gitHash = this.getResponseProperty("GitHash");
        this.server = new bw_ThirdPartyServerConfigResponse(this.getResponseProperty("Server"));
        this.environment = new bw_EnvironmentServerConfigResponse(this.getResponseProperty("Environment"));
        this.featureStates = this.getResponseProperty("FeatureStates");
        this.push = new bw_PushSettingsConfigResponse(this.getResponseProperty("Push"));
        this.settings = new bw_ServerSettings(this.getResponseProperty("Settings"));
    }
}
class bw_PushSettingsConfigResponse extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.pushTechnology = this.getResponseProperty("PushTechnology");
        this.vapidPublicKey = this.getResponseProperty("VapidPublicKey");
    }
}
class bw_EnvironmentServerConfigResponse extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.cloudRegion = this.getResponseProperty("CloudRegion");
        this.vault = this.getResponseProperty("Vault");
        this.api = this.getResponseProperty("Api");
        this.identity = this.getResponseProperty("Identity");
        this.notifications = this.getResponseProperty("Notifications");
        this.sso = this.getResponseProperty("Sso");
    }
}
class bw_ThirdPartyServerConfigResponse extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.name = this.getResponseProperty("Name");
        this.url = this.getResponseProperty("Url");
    }
}

;// ../../libs/common/src/platform/services/config/config-api.service.ts
var bw_config_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_ConfigApiService {
    constructor(apiService, tokenService) {
        this.apiService = apiService;
        this.tokenService = tokenService;
    }
    get(userId) {
        return bw_config_api_service_awaiter(this, void 0, void 0, function* () {
            // Authentication adds extra context to config responses, if the user has an access token, we want to use it
            // We don't particularly care about ensuring the token is valid and not expired, just that it exists
            const authed = userId == null ? false : (yield this.tokenService.getAccessToken(userId)) != null;
            const r = yield this.apiService.send("GET", "/config", null, authed, true);
            return new bw_ServerConfigResponse(r);
        });
    }
}

;// external "semver"
const bw_external_semver_namespaceObject = require("semver");
;// ../../libs/common/src/enums/push-technology.enum.ts
/**
 * The preferred push technology of the server.
 */
var bw_PushTechnology;
(function (PushTechnology) {
    /**
     * Indicates that we should use SignalR over web sockets to receive push notifications from the server.
     */
    PushTechnology[PushTechnology["SignalR"] = 0] = "SignalR";
    /**
     * Indicatates that we should use WebPush to receive push notifications from the server.
     */
    PushTechnology[PushTechnology["WebPush"] = 1] = "WebPush";
})(bw_PushTechnology || (bw_PushTechnology = {}));

;// ../../libs/common/src/platform/abstractions/config/server-config.ts

const bw_dayInMilliseconds = 24 * 3600 * 1000;
class bw_ServerConfig {
    constructor(serverConfigData) {
        var _a, _b;
        this.featureStates = {};
        this.version = serverConfigData.version;
        this.gitHash = serverConfigData.gitHash;
        this.server = serverConfigData.server;
        this.utcDate = new Date(serverConfigData.utcDate);
        this.environment = serverConfigData.environment;
        this.featureStates = serverConfigData.featureStates;
        this.push =
            serverConfigData.push == null
                ? {
                    pushTechnology: bw_PushTechnology.SignalR,
                }
                : {
                    pushTechnology: serverConfigData.push.pushTechnology,
                    vapidPublicKey: serverConfigData.push.vapidPublicKey,
                };
        this.settings = serverConfigData.settings;
        if (((_a = this.server) === null || _a === void 0 ? void 0 : _a.name) == null && ((_b = this.server) === null || _b === void 0 ? void 0 : _b.url) == null) {
            this.server = null;
        }
    }
    getAgeInMilliseconds() {
        var _a;
        return new Date().getTime() - ((_a = this.utcDate) === null || _a === void 0 ? void 0 : _a.getTime());
    }
    isValid() {
        return this.getAgeInMilliseconds() <= bw_dayInMilliseconds;
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        return new bw_ServerConfig(obj);
    }
}

;// ../../libs/common/src/platform/misc/flags.ts
function bw_getFlags(envFlags) {
    if (typeof envFlags === "string") {
        return JSON.parse(envFlags);
    }
    else {
        return envFlags;
    }
}
/**
 * Gets the value of a feature flag from environment.
 * All flags default to "on" (true).
 * Only use for shared code in `libs`, otherwise use the client-specific function.
 * @param flag The name of the feature flag to check
 * @returns The value of the flag
 */
function bw_flagEnabled(flag) {
    var _a;
    const flags = (_a = bw_getFlags({"sdk":true})) !== null && _a !== void 0 ? _a : {};
    return flags[flag] == null || !!flags[flag];
}
/**
 * Gets the value of a dev flag from environment.
 * Will always return false unless in development.
 * Only use for shared code in `libs`, otherwise use the client-specific function.
 * @param flag The name of the dev flag to check
 * @returns The value of the flag
 */
function bw_devFlagEnabled(flag) {
    if (true) {
        return false;
    }
    const devFlags = bw_getFlags({});
    return (devFlags === null || devFlags === void 0 ? void 0 : devFlags[flag]) == null ? false : !!devFlags[flag];
}
/**
 * Gets the value of a dev flag from environment.
 * Will always return false unless in development.
 * @param flag The name of the dev flag to check
 * @returns The value of the flag
 * @throws Error if the flag is not enabled
 */
function bw_devFlagValue(flag) {
    if (!bw_devFlagEnabled(flag)) {
        throw new Error(`This method should not be called, it is protected by a disabled dev flag.`);
    }
    const devFlags = bw_getFlags({});
    return devFlags[flag];
}

;// ../../libs/common/src/platform/models/data/server-config.data.ts

class bw_ServerConfigData {
    constructor(serverConfigResponse) {
        this.featureStates = {};
        this.version = serverConfigResponse === null || serverConfigResponse === void 0 ? void 0 : serverConfigResponse.version;
        this.gitHash = serverConfigResponse === null || serverConfigResponse === void 0 ? void 0 : serverConfigResponse.gitHash;
        this.server = (serverConfigResponse === null || serverConfigResponse === void 0 ? void 0 : serverConfigResponse.server)
            ? new bw_ThirdPartyServerConfigData(serverConfigResponse.server)
            : null;
        this.utcDate = new Date().toISOString();
        this.environment = (serverConfigResponse === null || serverConfigResponse === void 0 ? void 0 : serverConfigResponse.environment)
            ? new bw_EnvironmentServerConfigData(serverConfigResponse.environment)
            : null;
        this.featureStates = serverConfigResponse === null || serverConfigResponse === void 0 ? void 0 : serverConfigResponse.featureStates;
        this.settings = new bw_ServerSettings(serverConfigResponse.settings);
        this.push = (serverConfigResponse === null || serverConfigResponse === void 0 ? void 0 : serverConfigResponse.push)
            ? new bw_PushSettingsConfigData(serverConfigResponse.push)
            : null;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_ServerConfigData({}), obj, {
            server: (obj === null || obj === void 0 ? void 0 : obj.server) ? bw_ThirdPartyServerConfigData.fromJSON(obj.server) : null,
            environment: (obj === null || obj === void 0 ? void 0 : obj.environment) ? bw_EnvironmentServerConfigData.fromJSON(obj.environment) : null,
        });
    }
}
class bw_PushSettingsConfigData {
    constructor(response) {
        this.pushTechnology = response.pushTechnology;
        this.vapidPublicKey = response.vapidPublicKey;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_PushSettingsConfigData({}), obj);
    }
}
class bw_ThirdPartyServerConfigData {
    constructor(response) {
        this.name = response.name;
        this.url = response.url;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_ThirdPartyServerConfigData({}), obj);
    }
}
class bw_EnvironmentServerConfigData {
    constructor(response) {
        this.cloudRegion = response.cloudRegion;
        this.vault = response.vault;
        this.api = response.api;
        this.identity = response.identity;
        this.notifications = response.notifications;
        this.sso = response.sso;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_EnvironmentServerConfigData({}), obj);
    }
}

;// ../../libs/common/src/platform/services/config/default-config.service.ts
var bw_default_config_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










const bw_RETRIEVAL_INTERVAL = bw_devFlagEnabled("configRetrievalIntervalMs")
    ? bw_devFlagValue("configRetrievalIntervalMs")
    : 3600000; // 1 hour
const bw_SLOW_EMISSION_GUARD = 800;
const bw_USER_SERVER_CONFIG = new bw_UserKeyDefinition(bw_CONFIG_DISK, "serverConfig", {
    deserializer: (data) => (data == null ? null : bw_ServerConfig.fromJSON(data)),
    clearOn: ["logout"],
});
const bw_GLOBAL_SERVER_CONFIGURATIONS = bw_KeyDefinition.record(bw_CONFIG_DISK, "byServer", {
    deserializer: (data) => (data == null ? null : bw_ServerConfig.fromJSON(data)),
});
// FIXME: currently we are limited to api requests for active users. Update to accept a UserId and APIUrl once ApiService supports it.
class bw_DefaultConfigService {
    constructor(configApiService, environmentService, logService, stateProvider, authService) {
        this.configApiService = configApiService;
        this.environmentService = environmentService;
        this.logService = logService;
        this.stateProvider = stateProvider;
        this.authService = authService;
        this.failedFetchFallbackSubject = new bw_external_rxjs_namespaceObject.Subject();
        const userId$ = this.stateProvider.activeUserId$;
        const authStatus$ = userId$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => (userId == null ? (0,bw_external_rxjs_namespaceObject.of)(null) : this.authService.authStatusFor$(userId))));
        this.serverConfig$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([
            userId$,
            this.environmentService.environment$,
            authStatus$,
        ]).pipe((0,bw_external_rxjs_namespaceObject.switchMap)(([userId, environment, authStatus]) => {
            if (userId == null || authStatus !== bw_authentication_status_AuthenticationStatus.Unlocked) {
                return this.globalConfigFor$(environment.getApiUrl()).pipe((0,bw_external_rxjs_namespaceObject.map)((config) => [config, null, environment]));
            }
            return this.userConfigFor$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((config) => [config, userId, environment]));
        }), (0,bw_external_rxjs_namespaceObject.tap)((rec) => bw_default_config_service_awaiter(this, void 0, void 0, function* () {
            const [existingConfig, userId, environment] = rec;
            // Grab new config if older retrieval interval
            if (!existingConfig || this.olderThanRetrievalInterval(existingConfig.utcDate)) {
                yield this.renewConfig(existingConfig, userId, environment);
            }
        })), (0,bw_external_rxjs_namespaceObject.switchMap)(([existingConfig]) => {
            // If we needed to fetch, stop this emit, we'll get a new one after update
            // This is split up with the above tap because we need to return an observable from a failed promise,
            // which isn't very doable since promises are converted to observables in switchMap
            if (!existingConfig || this.olderThanRetrievalInterval(existingConfig.utcDate)) {
                return bw_external_rxjs_namespaceObject.NEVER;
            }
            return (0,bw_external_rxjs_namespaceObject.of)(existingConfig);
        }), 
        // If fetch fails, we'll emit on this subject to fallback to the existing config
        (0,bw_external_rxjs_namespaceObject.mergeWith)(this.failedFetchFallbackSubject), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        this.cloudRegion$ = this.serverConfig$.pipe((0,bw_external_rxjs_namespaceObject.map)((config) => { var _a, _b; return (_b = (_a = config === null || config === void 0 ? void 0 : config.environment) === null || _a === void 0 ? void 0 : _a.cloudRegion) !== null && _b !== void 0 ? _b : bw_Region.US; }));
        this.serverSettings$ = this.serverConfig$.pipe((0,bw_external_rxjs_namespaceObject.map)((config) => { var _a; return (_a = config === null || config === void 0 ? void 0 : config.settings) !== null && _a !== void 0 ? _a : new bw_ServerSettings(); }));
    }
    getFeatureFlag$(key) {
        return this.serverConfig$.pipe((0,bw_external_rxjs_namespaceObject.map)((serverConfig) => this.getFeatureFlagValue(serverConfig, key)));
    }
    getFeatureFlagValue(serverConfig, flag) {
        if ((serverConfig === null || serverConfig === void 0 ? void 0 : serverConfig.featureStates) == null || serverConfig.featureStates[flag] == null) {
            return bw_DefaultFeatureFlagValue[flag];
        }
        return serverConfig.featureStates[flag];
    }
    userCachedFeatureFlag$(key, userId) {
        return this.stateProvider
            .getUser(userId, bw_USER_SERVER_CONFIG)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((config) => this.getFeatureFlagValue(config, key)));
    }
    getFeatureFlag(key) {
        return bw_default_config_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.getFeatureFlag$(key));
        });
    }
    checkServerMeetsVersionRequirement$(minimumRequiredServerVersion) {
        return this.serverConfig$.pipe((0,bw_external_rxjs_namespaceObject.map)((serverConfig) => {
            if (serverConfig == null) {
                return false;
            }
            const serverVersion = new bw_external_semver_namespaceObject.SemVer(serverConfig.version);
            return serverVersion.compare(minimumRequiredServerVersion) >= 0;
        }));
    }
    ensureConfigFetched() {
        return bw_default_config_service_awaiter(this, void 0, void 0, function* () {
            // Triggering a retrieval for the given user ensures that the config is less than RETRIEVAL_INTERVAL old
            yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.serverConfig$);
        });
    }
    olderThanRetrievalInterval(date) {
        return new Date().getTime() - date.getTime() > bw_RETRIEVAL_INTERVAL;
    }
    // Updates the on-disk configuration with a newly retrieved configuration
    renewConfig(existingConfig, userId, environment) {
        return bw_default_config_service_awaiter(this, void 0, void 0, function* () {
            var _a, _b, _c;
            try {
                // Feature flags often have a big impact on user experience, lets ensure we return some value
                // somewhat quickly even though it may not be accurate, we won't cancel the HTTP request
                // though so that hopefully it can have finished and hydrated a more accurate value.
                const handle = setTimeout(() => {
                    this.logService.info("Self-host environment did not respond in time, emitting previous config.");
                    this.failedFetchFallbackSubject.next(existingConfig);
                }, bw_SLOW_EMISSION_GUARD);
                const response = yield this.configApiService.get(userId);
                clearTimeout(handle);
                const newConfig = new bw_ServerConfig(new bw_ServerConfigData(response));
                // Update the environment region
                if (((_a = newConfig === null || newConfig === void 0 ? void 0 : newConfig.environment) === null || _a === void 0 ? void 0 : _a.cloudRegion) != null &&
                    ((_b = existingConfig === null || existingConfig === void 0 ? void 0 : existingConfig.environment) === null || _b === void 0 ? void 0 : _b.cloudRegion) != newConfig.environment.cloudRegion) {
                    // Null userId sets global, otherwise sets to the given user
                    yield this.environmentService.setCloudRegion(userId, (_c = newConfig === null || newConfig === void 0 ? void 0 : newConfig.environment) === null || _c === void 0 ? void 0 : _c.cloudRegion);
                }
                if (userId == null) {
                    // update global state with new pulled config
                    yield this.stateProvider.getGlobal(bw_GLOBAL_SERVER_CONFIGURATIONS).update((configs) => {
                        return Object.assign(Object.assign({}, configs), { [environment.getApiUrl()]: newConfig });
                    });
                }
                else {
                    // update state with new pulled config
                    yield this.stateProvider.setUserState(bw_USER_SERVER_CONFIG, newConfig, userId);
                }
            }
            catch (e) {
                // mutate error to be handled by catchError
                this.logService.error(`Unable to fetch ServerConfig from ${environment.getApiUrl()}`, e);
                // Emit the existing config
                this.failedFetchFallbackSubject.next(existingConfig);
            }
        });
    }
    globalConfigFor$(apiUrl) {
        return this.stateProvider
            .getGlobal(bw_GLOBAL_SERVER_CONFIGURATIONS)
            .state$.pipe((0,bw_external_rxjs_namespaceObject.map)((configs) => configs === null || configs === void 0 ? void 0 : configs[apiUrl]));
    }
    userConfigFor$(userId) {
        return this.stateProvider.getUser(userId, bw_USER_SERVER_CONFIG).state$;
    }
}

;// ../../libs/common/src/platform/services/container.service.ts
class bw_ContainerService {
    constructor(keyService, encryptService) {
        this.keyService = keyService;
        this.encryptService = encryptService;
    }
    attachToGlobal(global) {
        if (!global.bitwardenContainerService) {
            global.bitwardenContainerService = this;
        }
    }
    /**
     * @throws Will throw if KeyService was not instantiated and provided to the ContainerService constructor
     */
    getKeyService() {
        if (this.keyService == null) {
            throw new Error("ContainerService.keyService not initialized.");
        }
        return this.keyService;
    }
    /**
     * @throws Will throw if EncryptService was not instantiated and provided to the ContainerService constructor
     */
    getEncryptService() {
        if (this.encryptService == null) {
            throw new Error("ContainerService.encryptService not initialized.");
        }
        return this.encryptService;
    }
}

;// ../../libs/common/src/platform/services/default-environment.service.ts
var bw_default_environment_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_EnvironmentUrls {
    constructor() {
        this.base = null;
        this.api = null;
        this.identity = null;
        this.icons = null;
        this.notifications = null;
        this.events = null;
        this.webVault = null;
        this.keyConnector = null;
    }
}
class bw_EnvironmentState {
    static fromJSON(obj) {
        return Object.assign(new bw_EnvironmentState(), obj);
    }
}
const bw_GLOBAL_ENVIRONMENT_KEY = new bw_KeyDefinition(bw_ENVIRONMENT_DISK, "environment", {
    deserializer: bw_EnvironmentState.fromJSON,
});
const bw_USER_ENVIRONMENT_KEY = new bw_UserKeyDefinition(bw_ENVIRONMENT_DISK, "environment", {
    deserializer: bw_EnvironmentState.fromJSON,
    clearOn: ["logout"],
});
const bw_GLOBAL_CLOUD_REGION_KEY = new bw_KeyDefinition(bw_ENVIRONMENT_MEMORY, "cloudRegion", {
    deserializer: (b) => b,
});
const bw_USER_CLOUD_REGION_KEY = new bw_UserKeyDefinition(bw_ENVIRONMENT_MEMORY, "cloudRegion", {
    deserializer: (b) => b,
    clearOn: ["logout"],
});
/**
 * The production regions available for selection.
 *
 * In the future we desire to load these urls from the config endpoint.
 */
const bw_PRODUCTION_REGIONS = [
    {
        key: bw_Region.US,
        domain: "bitwarden.com",
        urls: {
            base: null,
            api: "https://api.bitwarden.com",
            identity: "https://identity.bitwarden.com",
            icons: "https://icons.bitwarden.net",
            webVault: "https://vault.bitwarden.com",
            notifications: "https://notifications.bitwarden.com",
            events: "https://events.bitwarden.com",
            scim: "https://scim.bitwarden.com",
        },
    },
    {
        key: bw_Region.EU,
        domain: "bitwarden.eu",
        urls: {
            base: null,
            api: "https://api.bitwarden.eu",
            identity: "https://identity.bitwarden.eu",
            icons: "https://icons.bitwarden.eu",
            webVault: "https://vault.bitwarden.eu",
            notifications: "https://notifications.bitwarden.eu",
            events: "https://events.bitwarden.eu",
            scim: "https://scim.bitwarden.eu",
        },
    },
];
/**
 * The default region when starting the app.
 */
const bw_DEFAULT_REGION = bw_Region.US;
/**
 * The default region configuration.
 */
const bw_DEFAULT_REGION_CONFIG = bw_PRODUCTION_REGIONS.find((r) => r.key === bw_DEFAULT_REGION);
class bw_DefaultEnvironmentService {
    constructor(stateProvider, accountService, additionalRegionConfigs = []) {
        this.stateProvider = stateProvider;
        this.accountService = accountService;
        this.additionalRegionConfigs = additionalRegionConfigs;
        // We intentionally don't want the helper on account service, we want the null back if there is no active user
        this.activeAccountId$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id));
        this.globalState = this.stateProvider.getGlobal(bw_GLOBAL_ENVIRONMENT_KEY);
        this.globalCloudRegionState = this.stateProvider.getGlobal(bw_GLOBAL_CLOUD_REGION_KEY);
        const account$ = this.activeAccountId$.pipe(
        // Use == here to not trigger on undefined -> null transition
        (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)((oldUserId, newUserId) => oldUserId == newUserId));
        this.environment$ = account$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => {
            const t = userId
                ? this.stateProvider.getUser(userId, bw_USER_ENVIRONMENT_KEY).state$
                : this.stateProvider.getGlobal(bw_GLOBAL_ENVIRONMENT_KEY).state$;
            return t;
        }), (0,bw_external_rxjs_namespaceObject.map)((state) => {
            return this.buildEnvironment(state === null || state === void 0 ? void 0 : state.region, state === null || state === void 0 ? void 0 : state.urls);
        }));
        this.cloudWebVaultUrl$ = account$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => {
            const t = userId
                ? this.stateProvider.getUser(userId, bw_USER_CLOUD_REGION_KEY).state$
                : this.stateProvider.getGlobal(bw_GLOBAL_CLOUD_REGION_KEY).state$;
            return t;
        }), (0,bw_external_rxjs_namespaceObject.map)((region) => {
            if (region != null) {
                const config = this.getRegionConfig(region);
                if (config != null) {
                    return config.urls.webVault;
                }
            }
            return bw_DEFAULT_REGION_CONFIG.urls.webVault;
        }));
    }
    availableRegions() {
        return bw_PRODUCTION_REGIONS.concat(this.additionalRegionConfigs);
    }
    /**
     * Get the region configuration for the given region.
     */
    getRegionConfig(region) {
        return this.availableRegions().find((r) => r.key === region);
    }
    setEnvironment(region, urls) {
        return bw_default_environment_service_awaiter(this, void 0, void 0, function* () {
            // Unknown regions are treated as self-hosted
            if (this.getRegionConfig(region) == null) {
                region = bw_Region.SelfHosted;
            }
            // If self-hosted ensure urls are valid else fallback to default region
            if (region == bw_Region.SelfHosted && bw_isEmpty(urls)) {
                region = bw_DEFAULT_REGION;
            }
            if (region != bw_Region.SelfHosted) {
                yield this.globalState.update(() => ({
                    region: region,
                    urls: null,
                }));
                return null;
            }
            else {
                // Clean the urls
                urls.base = bw_formatUrl(urls.base);
                urls.webVault = bw_formatUrl(urls.webVault);
                urls.api = bw_formatUrl(urls.api);
                urls.identity = bw_formatUrl(urls.identity);
                urls.icons = bw_formatUrl(urls.icons);
                urls.notifications = bw_formatUrl(urls.notifications);
                urls.events = bw_formatUrl(urls.events);
                urls.keyConnector = bw_formatUrl(urls.keyConnector);
                urls.scim = null;
                yield this.globalState.update(() => ({
                    region: region,
                    urls: {
                        base: urls.base,
                        api: urls.api,
                        identity: urls.identity,
                        webVault: urls.webVault,
                        icons: urls.icons,
                        notifications: urls.notifications,
                        events: urls.events,
                        keyConnector: urls.keyConnector,
                    },
                }));
                return urls;
            }
        });
    }
    /**
     * Helper for building the environment from state. Performs some general sanitization to avoid invalid regions and urls.
     */
    buildEnvironment(region, urls) {
        // Unknown regions are treated as self-hosted
        if (this.getRegionConfig(region) == null) {
            region = bw_Region.SelfHosted;
        }
        // If self-hosted ensure urls are valid else fallback to default region
        if (region == bw_Region.SelfHosted && bw_isEmpty(urls)) {
            region = bw_DEFAULT_REGION;
        }
        // Load urls from region config
        if (region != bw_Region.SelfHosted) {
            const regionConfig = this.getRegionConfig(region);
            if (regionConfig != null) {
                return new bw_CloudEnvironment(regionConfig);
            }
        }
        return new bw_SelfHostedEnvironment(urls);
    }
    setCloudRegion(userId, region) {
        return bw_default_environment_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                yield this.globalCloudRegionState.update(() => region);
            }
            else {
                yield this.stateProvider.getUser(userId, bw_USER_CLOUD_REGION_KEY).update(() => region);
            }
        });
    }
    getEnvironment$(userId) {
        return this.stateProvider.getUser(userId, bw_USER_ENVIRONMENT_KEY).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((state) => {
            return this.buildEnvironment(state === null || state === void 0 ? void 0 : state.region, state === null || state === void 0 ? void 0 : state.urls);
        }));
    }
    /**
     * @deprecated Use getEnvironment$ instead.
     */
    getEnvironment(userId) {
        return bw_default_environment_service_awaiter(this, void 0, void 0, function* () {
            // Add backwards compatibility support for null userId
            const definedUserId = userId !== null && userId !== void 0 ? userId : (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeAccountId$));
            return (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.getEnvironment$(definedUserId));
        });
    }
    seedUserEnvironment(userId) {
        return bw_default_environment_service_awaiter(this, void 0, void 0, function* () {
            const global = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.globalState.state$);
            yield this.stateProvider.getUser(userId, bw_USER_ENVIRONMENT_KEY).update(() => global);
        });
    }
}
function bw_formatUrl(url) {
    if (url == null || url === "") {
        return null;
    }
    url = url.replace(/\/+$/g, "");
    if (!url.startsWith("http://") && !url.startsWith("https://")) {
        url = "https://" + url;
    }
    return url.trim();
}
function bw_isEmpty(u) {
    if (u == null) {
        return true;
    }
    return (u.base == null &&
        u.webVault == null &&
        u.api == null &&
        u.identity == null &&
        u.icons == null &&
        u.notifications == null &&
        u.events == null);
}
class bw_UrlEnvironment {
    constructor(region, urls) {
        this.region = region;
        this.urls = urls;
        // Scim is always null for self-hosted
        if (region == bw_Region.SelfHosted) {
            this.urls.scim = null;
        }
    }
    getRegion() {
        return this.region;
    }
    getUrls() {
        return {
            base: this.urls.base,
            webVault: this.urls.webVault,
            api: this.urls.api,
            identity: this.urls.identity,
            icons: this.urls.icons,
            notifications: this.urls.notifications,
            events: this.urls.events,
            keyConnector: this.urls.keyConnector,
            scim: this.urls.scim,
        };
    }
    hasBaseUrl() {
        return this.urls.base != null;
    }
    getWebVaultUrl() {
        return this.getUrl("webVault", "");
    }
    getApiUrl() {
        return this.getUrl("api", "/api");
    }
    getEventsUrl() {
        return this.getUrl("events", "/events");
    }
    getIconsUrl() {
        return this.getUrl("icons", "/icons");
    }
    getIdentityUrl() {
        return this.getUrl("identity", "/identity");
    }
    getKeyConnectorUrl() {
        return this.urls.keyConnector;
    }
    getNotificationsUrl() {
        return this.getUrl("notifications", "/notifications");
    }
    getScimUrl() {
        if (this.urls.scim != null) {
            return this.urls.scim + "/v2";
        }
        return this.getWebVaultUrl() === "https://vault.bitwarden.com"
            ? "https://scim.bitwarden.com/v2"
            : this.getWebVaultUrl() + "/scim/v2";
    }
    getSendUrl() {
        return this.getWebVaultUrl() === "https://vault.bitwarden.com"
            ? "https://send.bitwarden.com/#"
            : this.getWebVaultUrl() + "/#/send/";
    }
    /**
     * Presume that if the region is not self-hosted, it is cloud.
     */
    isCloud() {
        return this.region !== bw_Region.SelfHosted;
    }
    /**
     * Helper for getting an URL.
     *
     * @param key Key of the URL to get from URLs
     * @param baseSuffix Suffix to append to the base URL if the url is not set
     * @returns
     */
    getUrl(key, baseSuffix) {
        if (this.urls[key] != null) {
            return this.urls[key];
        }
        if (this.urls.base) {
            return this.urls.base + baseSuffix;
        }
        return bw_DEFAULT_REGION_CONFIG.urls[key];
    }
}
/**
 * Denote a cloud environment.
 */
class bw_CloudEnvironment extends bw_UrlEnvironment {
    constructor(config) {
        super(config.key, config.urls);
        this.config = config;
    }
    /**
     * Cloud always returns nice urls, i.e. bitwarden.com instead of vault.bitwarden.com.
     */
    getHostname() {
        return this.config.domain;
    }
}
class bw_SelfHostedEnvironment extends bw_UrlEnvironment {
    constructor(urls) {
        super(bw_Region.SelfHosted, urls);
    }
    getHostname() {
        return bw_utils_Utils.getHost(this.getWebVaultUrl());
    }
}

;// ../../libs/common/src/platform/services/file-upload/azure-file-upload.service.ts
var bw_azure_file_upload_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_MAX_SINGLE_BLOB_UPLOAD_SIZE = 256 * 1024 * 1024; // 256 MiB
const bw_MAX_BLOCKS_PER_BLOB = 50000;
class bw_AzureFileUploadService {
    constructor(logService, apiService) {
        this.logService = logService;
        this.apiService = apiService;
    }
    upload(url, data, renewalCallback) {
        return bw_azure_file_upload_service_awaiter(this, void 0, void 0, function* () {
            if (data.buffer.byteLength <= bw_MAX_SINGLE_BLOB_UPLOAD_SIZE) {
                return yield this.azureUploadBlob(url, data);
            }
            else {
                return yield this.azureUploadBlocks(url, data, renewalCallback);
            }
        });
    }
    azureUploadBlob(url, data) {
        return bw_azure_file_upload_service_awaiter(this, void 0, void 0, function* () {
            const urlObject = bw_utils_Utils.getUrl(url);
            const headers = new Headers({
                "x-ms-date": new Date().toUTCString(),
                "x-ms-version": urlObject.searchParams.get("sv"),
                "Content-Length": data.buffer.byteLength.toString(),
                "x-ms-blob-type": "BlockBlob",
            });
            const request = new Request(url, {
                body: data.buffer,
                cache: "no-store",
                method: "PUT",
                headers: headers,
            });
            const blobResponse = yield this.apiService.nativeFetch(request);
            if (blobResponse.status !== 201) {
                throw new Error(`Failed to create Azure blob: ${blobResponse.status}`);
            }
        });
    }
    azureUploadBlocks(url, data, renewalCallback) {
        return bw_azure_file_upload_service_awaiter(this, void 0, void 0, function* () {
            const baseUrl = bw_utils_Utils.getUrl(url);
            const blockSize = this.getMaxBlockSize(baseUrl.searchParams.get("sv"));
            let blockIndex = 0;
            const numBlocks = Math.ceil(data.buffer.byteLength / blockSize);
            const blocksStaged = [];
            if (numBlocks > bw_MAX_BLOCKS_PER_BLOB) {
                throw new Error(`Cannot upload file, exceeds maximum size of ${blockSize * bw_MAX_BLOCKS_PER_BLOB}`);
            }
            // eslint-disable-next-line
            try {
                while (blockIndex < numBlocks) {
                    url = yield this.renewUrlIfNecessary(url, renewalCallback);
                    const blockUrl = bw_utils_Utils.getUrl(url);
                    const blockId = this.encodedBlockId(blockIndex);
                    blockUrl.searchParams.append("comp", "block");
                    blockUrl.searchParams.append("blockid", blockId);
                    const start = blockIndex * blockSize;
                    const blockData = data.buffer.slice(start, start + blockSize);
                    const blockHeaders = new Headers({
                        "x-ms-date": new Date().toUTCString(),
                        "x-ms-version": blockUrl.searchParams.get("sv"),
                        "Content-Length": blockData.byteLength.toString(),
                    });
                    const blockRequest = new Request(blockUrl.toString(), {
                        body: blockData,
                        cache: "no-store",
                        method: "PUT",
                        headers: blockHeaders,
                    });
                    const blockResponse = yield this.apiService.nativeFetch(blockRequest);
                    if (blockResponse.status !== 201) {
                        const message = `Unsuccessful block PUT. Received status ${blockResponse.status}`;
                        this.logService.error(message + "\n" + (yield blockResponse.json()));
                        throw new Error(message);
                    }
                    blocksStaged.push(blockId);
                    blockIndex++;
                }
                url = yield this.renewUrlIfNecessary(url, renewalCallback);
                const blockListUrl = bw_utils_Utils.getUrl(url);
                const blockListXml = this.blockListXml(blocksStaged);
                blockListUrl.searchParams.append("comp", "blocklist");
                const headers = new Headers({
                    "x-ms-date": new Date().toUTCString(),
                    "x-ms-version": blockListUrl.searchParams.get("sv"),
                    "Content-Length": blockListXml.length.toString(),
                });
                const request = new Request(blockListUrl.toString(), {
                    body: blockListXml,
                    cache: "no-store",
                    method: "PUT",
                    headers: headers,
                });
                const response = yield this.apiService.nativeFetch(request);
                if (response.status !== 201) {
                    const message = `Unsuccessful block list PUT. Received status ${response.status}`;
                    this.logService.error(message + "\n" + (yield response.json()));
                    throw new Error(message);
                }
            }
            catch (e) {
                throw e;
            }
        });
    }
    renewUrlIfNecessary(url, renewalCallback) {
        return bw_azure_file_upload_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const urlObject = bw_utils_Utils.getUrl(url);
            const expiry = new Date((_a = urlObject.searchParams.get("se")) !== null && _a !== void 0 ? _a : "");
            if (isNaN(expiry.getTime())) {
                expiry.setTime(Date.now() + 3600000);
            }
            if (expiry.getTime() < Date.now() + 1000) {
                return yield renewalCallback();
            }
            return url;
        });
    }
    encodedBlockId(blockIndex) {
        // Encoded blockId max size is 64, so pre-encoding max size is 48
        const utfBlockId = ("000000000000000000000000000000000000000000000000" + blockIndex.toString()).slice(-48);
        return bw_utils_Utils.fromUtf8ToB64(utfBlockId);
    }
    blockListXml(blockIdList) {
        let xml = '<?xml version="1.0" encoding="utf-8"?><BlockList>';
        blockIdList.forEach((blockId) => {
            xml += `<Latest>${blockId}</Latest>`;
        });
        xml += "</BlockList>";
        return xml;
    }
    getMaxBlockSize(version) {
        if (bw_Version.compare(version, "2019-12-12") >= 0) {
            return 4000 * 1024 * 1024; // 4000 MiB
        }
        else if (bw_Version.compare(version, "2016-05-31") >= 0) {
            return 100 * 1024 * 1024; // 100 MiB
        }
        else {
            return 4 * 1024 * 1024; // 4 MiB
        }
    }
}
class bw_Version {
    /**
     * Compares two Azure Versions against each other
     * @param a Version to compare
     * @param b Version to compare
     * @returns a number less than zero if b is newer than a, 0 if equal,
     * and greater than zero if a is newer than b
     */
    static compare(a, b) {
        if (typeof a === "string") {
            a = new bw_Version(a);
        }
        if (typeof b === "string") {
            b = new bw_Version(b);
        }
        return a.year !== b.year
            ? a.year - b.year
            : a.month !== b.month
                ? a.month - b.month
                : a.day !== b.day
                    ? a.day - b.day
                    : 0;
    }
    constructor(version) {
        this.year = 0;
        this.month = 0;
        this.day = 0;
        try {
            const parts = version.split("-").map((v) => Number.parseInt(v, 10));
            this.year = parts[0];
            this.month = parts[1];
            this.day = parts[2];
        }
        catch (_a) {
            // Ignore error
        }
    }
    /**
     * Compares two Azure Versions against each other
     * @param compareTo Version to compare against
     * @returns a number less than zero if compareTo is newer, 0 if equal,
     * and greater than zero if this is greater than compareTo
     */
    compare(compareTo) {
        return bw_Version.compare(this, compareTo);
    }
}

;// ../../libs/common/src/platform/services/file-upload/bitwarden-file-upload.service.ts
var bw_bitwarden_file_upload_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_BitwardenFileUploadService {
    upload(encryptedFileName, encryptedFileData, apiCall) {
        return bw_bitwarden_file_upload_service_awaiter(this, void 0, void 0, function* () {
            const fd = new FormData();
            if (bw_utils_Utils.isBrowser) {
                const blob = new Blob([encryptedFileData.buffer], { type: "application/octet-stream" });
                fd.append("data", blob, encryptedFileName);
            }
            else if (bw_utils_Utils.isNode) {
                fd.append("data", Buffer.from(encryptedFileData.buffer), {
                    filename: encryptedFileName,
                    contentType: "application/octet-stream",
                });
            }
            else {
                throw new Error("Unsupported environment");
            }
            yield apiCall(fd);
        });
    }
}

;// ../../libs/common/src/platform/services/file-upload/file-upload.service.ts
var bw_file_upload_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_FileUploadService {
    constructor(logService, apiService) {
        this.logService = logService;
        this.azureFileUploadService = new bw_AzureFileUploadService(logService, apiService);
        this.bitwardenFileUploadService = new bw_BitwardenFileUploadService();
    }
    upload(uploadData, fileName, encryptedFileData, fileUploadMethods) {
        return bw_file_upload_service_awaiter(this, void 0, void 0, function* () {
            try {
                switch (uploadData.fileUploadType) {
                    case bw_FileUploadType.Direct:
                        yield this.bitwardenFileUploadService.upload(fileName.encryptedString, encryptedFileData, (fd) => fileUploadMethods.postDirect(fd));
                        break;
                    case bw_FileUploadType.Azure: {
                        yield this.azureFileUploadService.upload(uploadData.url, encryptedFileData, fileUploadMethods.renewFileUploadUrl);
                        break;
                    }
                    default:
                        throw new Error("Unknown file upload type");
                }
            }
            catch (e) {
                yield fileUploadMethods.rollback();
                throw e;
            }
        });
    }
}

;// ../../libs/common/src/platform/services/key-generation.service.ts
var bw_key_generation_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_KeyGenerationService {
    constructor(cryptoFunctionService) {
        this.cryptoFunctionService = cryptoFunctionService;
    }
    createKey(bitLength) {
        return bw_key_generation_service_awaiter(this, void 0, void 0, function* () {
            const key = yield this.cryptoFunctionService.aesGenerateKey(bitLength);
            return new bw_SymmetricCryptoKey(key);
        });
    }
    createKeyWithPurpose(bitLength, purpose, salt) {
        return bw_key_generation_service_awaiter(this, void 0, void 0, function* () {
            if (salt == null) {
                const bytes = yield this.cryptoFunctionService.randomBytes(32);
                salt = bw_utils_Utils.fromBufferToUtf8(bytes);
            }
            const material = yield this.cryptoFunctionService.aesGenerateKey(bitLength);
            const key = yield this.cryptoFunctionService.hkdf(material, salt, purpose, 64, "sha256");
            return { salt, material, derivedKey: new bw_SymmetricCryptoKey(key) };
        });
    }
    deriveKeyFromMaterial(material, salt, purpose) {
        return bw_key_generation_service_awaiter(this, void 0, void 0, function* () {
            const key = yield this.cryptoFunctionService.hkdf(material, salt, purpose, 64, "sha256");
            return new bw_SymmetricCryptoKey(key);
        });
    }
    deriveKeyFromPassword(password, salt, kdfConfig) {
        return bw_key_generation_service_awaiter(this, void 0, void 0, function* () {
            let key = null;
            if (kdfConfig.kdfType == null || kdfConfig.kdfType === bw_KdfType.PBKDF2_SHA256) {
                if (kdfConfig.iterations == null) {
                    kdfConfig.iterations = bw_PBKDF2KdfConfig.ITERATIONS.defaultValue;
                }
                key = yield this.cryptoFunctionService.pbkdf2(password, salt, "sha256", kdfConfig.iterations);
            }
            else if (kdfConfig.kdfType == bw_KdfType.Argon2id) {
                if (kdfConfig.iterations == null) {
                    kdfConfig.iterations = bw_Argon2KdfConfig.ITERATIONS.defaultValue;
                }
                if (kdfConfig.memory == null) {
                    kdfConfig.memory = bw_Argon2KdfConfig.MEMORY.defaultValue;
                }
                if (kdfConfig.parallelism == null) {
                    kdfConfig.parallelism = bw_Argon2KdfConfig.PARALLELISM.defaultValue;
                }
                const saltHash = yield this.cryptoFunctionService.hash(salt, "sha256");
                key = yield this.cryptoFunctionService.argon2(password, saltHash, kdfConfig.iterations, kdfConfig.memory * 1024, // convert to KiB from MiB
                kdfConfig.parallelism);
            }
            else {
                throw new Error("Unknown Kdf.");
            }
            return new bw_SymmetricCryptoKey(key);
        });
    }
    stretchKey(key) {
        return bw_key_generation_service_awaiter(this, void 0, void 0, function* () {
            const newKey = new Uint8Array(64);
            const encKey = yield this.cryptoFunctionService.hkdfExpand(key.key, "enc", 32, "sha256");
            const macKey = yield this.cryptoFunctionService.hkdfExpand(key.key, "mac", 32, "sha256");
            newKey.set(new Uint8Array(encKey));
            newKey.set(new Uint8Array(macKey), 32);
            return new bw_SymmetricCryptoKey(newKey);
        });
    }
}

;// ../../libs/common/src/platform/abstractions/storage.service.ts
class bw_AbstractStorageService {
}

;// ../../libs/common/src/platform/services/memory-storage.service.ts
var bw_memory_storage_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_MemoryStorageService extends bw_AbstractStorageService {
    constructor() {
        super(...arguments);
        this.store = new Map();
        this.updatesSubject = new bw_external_rxjs_namespaceObject.Subject();
    }
    get valuesRequireDeserialization() {
        return false;
    }
    get updates$() {
        return this.updatesSubject.asObservable();
    }
    get(key) {
        if (this.store.has(key)) {
            const obj = this.store.get(key);
            return Promise.resolve(obj);
        }
        return Promise.resolve(null);
    }
    has(key) {
        return bw_memory_storage_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.get(key)) != null;
        });
    }
    save(key, obj) {
        if (obj == null) {
            return this.remove(key);
        }
        // TODO: Remove once foreground/background contexts are separated in browser
        // Needed to ensure ownership of all memory by the context running the storage service
        const toStore = structuredClone(obj);
        this.store.set(key, toStore);
        this.updatesSubject.next({ key, updateType: "save" });
        return Promise.resolve();
    }
    remove(key) {
        this.store.delete(key);
        this.updatesSubject.next({ key, updateType: "remove" });
        return Promise.resolve();
    }
}

;// ../../libs/common/src/state-migrations/migration-builder.ts
var bw_migration_builder_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_MigrationBuilder {
    /** Create a new MigrationBuilder with an empty buffer of migrations to perform.
     *
     * Add migrations to the buffer with {@link with} and {@link rollback}.
     * @returns A new MigrationBuilder.
     */
    static create() {
        return new bw_MigrationBuilder([]);
    }
    constructor(migrations) {
        this.migrations = migrations;
    }
    /** Add a migrator to the MigrationBuilder. Types are updated such that the chained MigrationBuilder must currently be
     * at state version equal to the from version of the migrator. Return as MigrationBuilder<TTo> where TTo is the to
     * version of the migrator, so that the next migrator can be chained.
     *
     * @param migrate A migrator class or a tuple of a migrator class, the from version, and the to version. A tuple is
     * required to instantiate version numbers unless a default constructor is defined.
     * @returns A new MigrationBuilder with the to version of the migrator as the current version.
     */
    with(...migrate) {
        return this.addMigrator(migrate, "up");
    }
    /** Add a migrator to rollback on the MigrationBuilder's list of migrations. As with {@link with}, types of
     * MigrationBuilder and Migrator must align. However, this time the migration is reversed so TCurrent of the
     * MigrationBuilder must be equal to the to version of the migrator. Return as MigrationBuilder<TFrom> where TFrom
     * is the from version of the migrator, so that the next migrator can be chained.
     *
     * @param migrate A migrator class or a tuple of a migrator class, the from version, and the to version. A tuple is
     * required to instantiate version numbers unless a default constructor is defined.
     * @returns A new MigrationBuilder with the from version of the migrator as the current version.
     */
    rollback(...migrate) {
        if (migrate.length === 3) {
            migrate = [migrate[0], migrate[2], migrate[1]];
        }
        return this.addMigrator(migrate, "down");
    }
    /** Execute the migrations as defined in the MigrationBuilder's migrator buffer */
    migrate(helper) {
        return this.migrations.reduce((promise, migrator) => promise.then(() => bw_migration_builder_awaiter(this, void 0, void 0, function* () {
            yield this.runMigrator(migrator.migrator, helper, migrator.direction);
        })), Promise.resolve());
    }
    addMigrator(migrate, direction = "up") {
        const newMigration = migrate.length === 1
            ? { migrator: new migrate[0](), direction }
            : { migrator: new migrate[0](migrate[1], migrate[2]), direction };
        return new bw_MigrationBuilder([...this.migrations, newMigration]);
    }
    runMigrator(migrator, helper, direction) {
        return bw_migration_builder_awaiter(this, void 0, void 0, function* () {
            const shouldMigrate = yield migrator.shouldMigrate(helper, direction);
            helper.info(`Migrator ${migrator.constructor.name} (to version ${migrator.toVersion}) should migrate: ${shouldMigrate} - ${direction}`);
            if (shouldMigrate) {
                const method = direction === "up" ? migrator.migrate : migrator.rollback;
                yield method.bind(migrator)(helper);
                helper.info(`Migrator ${migrator.constructor.name} (to version ${migrator.toVersion}) migrated - ${direction}`);
                yield migrator.updateVersion(helper, direction);
                helper.info(`Migrator ${migrator.constructor.name} (to version ${migrator.toVersion}) updated version - ${direction}`);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrator.ts
var bw_migrator_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
const bw_IRREVERSIBLE = new Error("Irreversible migration");
class bw_Migrator {
    constructor(fromVersion, toVersion) {
        this.fromVersion = fromVersion;
        this.toVersion = toVersion;
        if (fromVersion == null || toVersion == null) {
            throw new Error("Invalid migration");
        }
        if (fromVersion > toVersion) {
            throw new Error("Invalid migration");
        }
    }
    shouldMigrate(helper, direction) {
        const startVersion = direction === "up" ? this.fromVersion : this.toVersion;
        return Promise.resolve(helper.currentVersion === startVersion);
    }
    updateVersion(helper, direction) {
        return bw_migrator_awaiter(this, void 0, void 0, function* () {
            const endVersion = direction === "up" ? this.toVersion : this.fromVersion;
            helper.currentVersion = endVersion;
            yield helper.set("stateVersion", endVersion);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/10-move-ever-had-user-key-to-state-providers.ts
var bw_10_move_ever_had_user_key_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_10_move_ever_had_user_key_to_state_providers_USER_EVER_HAD_USER_KEY = {
    key: "everHadUserKey",
    stateDefinition: {
        name: "crypto",
    },
};
class bw_EverHadUserKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_10_move_ever_had_user_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_10_move_ever_had_user_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.everHadUserKey;
                    yield helper.setToUser(userId, bw_10_move_ever_had_user_key_to_state_providers_USER_EVER_HAD_USER_KEY, value !== null && value !== void 0 ? value : false);
                    if (value != null) {
                        delete account.profile.everHadUserKey;
                    }
                    yield helper.set(userId, account);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_10_move_ever_had_user_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_10_move_ever_had_user_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_10_move_ever_had_user_key_to_state_providers_USER_EVER_HAD_USER_KEY);
                    if (account) {
                        account.profile = Object.assign((_a = account.profile) !== null && _a !== void 0 ? _a : {}, {
                            everHadUserKey: value,
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_10_move_ever_had_user_key_to_state_providers_USER_EVER_HAD_USER_KEY, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/11-move-org-keys-to-state-providers.ts
var bw_11_move_org_keys_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_11_move_org_keys_to_state_providers_USER_ENCRYPTED_ORGANIZATION_KEYS = {
    key: "organizationKeys",
    stateDefinition: {
        name: "crypto",
    },
};
class bw_OrganizationKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_11_move_org_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_11_move_org_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.organizationKeys) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_11_move_org_keys_to_state_providers_USER_ENCRYPTED_ORGANIZATION_KEYS, value);
                        delete account.keys.organizationKeys;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_11_move_org_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_11_move_org_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_11_move_org_keys_to_state_providers_USER_ENCRYPTED_ORGANIZATION_KEYS);
                    if (account && value) {
                        account.keys = Object.assign((_a = account.keys) !== null && _a !== void 0 ? _a : {}, {
                            organizationKeys: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_11_move_org_keys_to_state_providers_USER_ENCRYPTED_ORGANIZATION_KEYS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/12-move-environment-state-to-providers.ts
var bw_12_move_environment_state_to_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_ENVIRONMENT_STATE = { name: "environment" };
const bw_REGION_KEY = { key: "region", stateDefinition: bw_ENVIRONMENT_STATE };
const bw_URLS_KEY = { key: "urls", stateDefinition: bw_ENVIRONMENT_STATE };
class bw_MoveEnvironmentStateToProviders extends bw_Migrator {
    migrate(helper) {
        return bw_12_move_environment_state_to_providers_awaiter(this, void 0, void 0, function* () {
            const legacyGlobal = yield helper.get("global");
            // Move global data
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.region) != null) {
                yield helper.setToGlobal(bw_REGION_KEY, legacyGlobal.region);
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.environmentUrls) != null) {
                yield helper.setToGlobal(bw_URLS_KEY, legacyGlobal.environmentUrls);
            }
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_12_move_environment_state_to_providers_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c, _d, _e;
                // Move account data
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.region) != null) {
                    yield helper.setToUser(userId, bw_REGION_KEY, account.settings.region);
                }
                if (((_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? void 0 : _c.environmentUrls) != null) {
                    yield helper.setToUser(userId, bw_URLS_KEY, account.settings.environmentUrls);
                }
                // Delete old account data
                (_d = account === null || account === void 0 ? void 0 : account.settings) === null || _d === void 0 ? true : delete _d.region;
                (_e = account === null || account === void 0 ? void 0 : account.settings) === null || _e === void 0 ? true : delete _e.environmentUrls;
                yield helper.set(userId, account);
            })));
            // Delete legacy global data
            legacyGlobal === null || legacyGlobal === void 0 ? true : delete legacyGlobal.region;
            legacyGlobal === null || legacyGlobal === void 0 ? true : delete legacyGlobal.environmentUrls;
            yield helper.set("global", legacyGlobal);
        });
    }
    rollback(helper) {
        return bw_12_move_environment_state_to_providers_awaiter(this, void 0, void 0, function* () {
            let legacyGlobal = yield helper.get("global");
            let updatedLegacyGlobal = false;
            const globalRegion = yield helper.getFromGlobal(bw_REGION_KEY);
            if (globalRegion) {
                if (!legacyGlobal) {
                    legacyGlobal = {};
                }
                updatedLegacyGlobal = true;
                legacyGlobal.region = globalRegion;
                yield helper.setToGlobal(bw_REGION_KEY, null);
            }
            const globalUrls = yield helper.getFromGlobal(bw_URLS_KEY);
            if (globalUrls) {
                if (!legacyGlobal) {
                    legacyGlobal = {};
                }
                updatedLegacyGlobal = true;
                legacyGlobal.environmentUrls = globalUrls;
                yield helper.setToGlobal(bw_URLS_KEY, null);
            }
            if (updatedLegacyGlobal) {
                yield helper.set("global", legacyGlobal);
            }
            function rollbackUser(userId, account) {
                return bw_12_move_environment_state_to_providers_awaiter(this, void 0, void 0, function* () {
                    let updatedAccount = false;
                    const userRegion = yield helper.getFromUser(userId, bw_REGION_KEY);
                    if (userRegion) {
                        if (!account) {
                            account = {};
                        }
                        if (!account.settings) {
                            account.settings = {};
                        }
                        updatedAccount = true;
                        account.settings.region = userRegion;
                        yield helper.setToUser(userId, bw_REGION_KEY, null);
                    }
                    const userUrls = yield helper.getFromUser(userId, bw_URLS_KEY);
                    if (userUrls) {
                        if (!account) {
                            account = {};
                        }
                        if (!account.settings) {
                            account.settings = {};
                        }
                        updatedAccount = true;
                        account.settings.environmentUrls = userUrls;
                        yield helper.setToUser(userId, bw_URLS_KEY, null);
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/13-move-provider-keys-to-state-providers.ts
var bw_13_move_provider_keys_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_13_move_provider_keys_to_state_providers_USER_ENCRYPTED_PROVIDER_KEYS = {
    key: "providerKeys",
    stateDefinition: {
        name: "crypto",
    },
};
class bw_ProviderKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_13_move_provider_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_13_move_provider_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.providerKeys) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_13_move_provider_keys_to_state_providers_USER_ENCRYPTED_PROVIDER_KEYS, value);
                        delete account.keys.providerKeys;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_13_move_provider_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_13_move_provider_keys_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_13_move_provider_keys_to_state_providers_USER_ENCRYPTED_PROVIDER_KEYS);
                    if (account && value) {
                        account.keys = Object.assign((_a = account.keys) !== null && _a !== void 0 ? _a : {}, {
                            providerKeys: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_13_move_provider_keys_to_state_providers_USER_ENCRYPTED_PROVIDER_KEYS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/14-move-biometric-client-key-half-state-to-providers.ts
var bw_14_move_biometric_client_key_half_state_to_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// Biometric text, no auto prompt text, fingerprint validated, and prompt cancelled are refreshed on every app start, so we don't need to migrate them
const bw_CLIENT_KEY_HALF = {
    key: "clientKeyHalf",
    stateDefinition: { name: "biometricSettings" },
};
class bw_MoveBiometricClientKeyHalfToStateProviders extends bw_Migrator {
    migrate(helper) {
        return bw_14_move_biometric_client_key_half_state_to_providers_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_14_move_biometric_client_key_half_state_to_providers_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c;
                // Move account data
                if (((_b = account === null || account === void 0 ? void 0 : account.keys) === null || _b === void 0 ? void 0 : _b.biometricEncryptionClientKeyHalf) != null) {
                    yield helper.setToUser(userId, bw_CLIENT_KEY_HALF, account.keys.biometricEncryptionClientKeyHalf);
                    // Delete old account data
                    (_c = account === null || account === void 0 ? void 0 : account.keys) === null || _c === void 0 ? true : delete _c.biometricEncryptionClientKeyHalf;
                    yield helper.set(userId, account);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_14_move_biometric_client_key_half_state_to_providers_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_14_move_biometric_client_key_half_state_to_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    let updatedAccount = false;
                    const userKeyHalf = yield helper.getFromUser(userId, bw_CLIENT_KEY_HALF);
                    if (userKeyHalf) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.keys) !== null && _a !== void 0 ? _a : (account.keys = {});
                        updatedAccount = true;
                        account.keys.biometricEncryptionClientKeyHalf = userKeyHalf;
                        yield helper.setToUser(userId, bw_CLIENT_KEY_HALF, null);
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/15-move-folder-state-to-state-provider.ts
var bw_15_move_folder_state_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_USER_ENCRYPTED_FOLDERS = {
    key: "folders",
    stateDefinition: {
        name: "folder",
    },
};
class bw_FolderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_15_move_folder_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_15_move_folder_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.folders) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_USER_ENCRYPTED_FOLDERS, value);
                        delete account.data.folders;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_15_move_folder_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_15_move_folder_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_USER_ENCRYPTED_FOLDERS);
                    if (account) {
                        account.data = Object.assign((_a = account.data) !== null && _a !== void 0 ? _a : {}, {
                            folders: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_USER_ENCRYPTED_FOLDERS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/16-move-last-sync-to-state-provider.ts
var bw_16_move_last_sync_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_LAST_SYNC_KEY = {
    key: "lastSync",
    stateDefinition: {
        name: "sync",
    },
};
class bw_LastSyncMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_16_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_16_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.lastSync;
                    yield helper.setToUser(userId, bw_LAST_SYNC_KEY, value !== null && value !== void 0 ? value : null);
                    if (value != null) {
                        delete account.profile.lastSync;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_16_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_16_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_LAST_SYNC_KEY);
                    if (account) {
                        account.profile = Object.assign((_a = account.profile) !== null && _a !== void 0 ? _a : {}, {
                            lastSync: value,
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_LAST_SYNC_KEY, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/17-move-enable-passkeys-to-state-providers.ts
var bw_17_move_enable_passkeys_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_USER_ENABLE_PASSKEYS = {
    key: "enablePasskeys",
    stateDefinition: {
        name: "vaultSettings",
    },
};
class bw_EnablePasskeysMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_17_move_enable_passkeys_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const global = yield helper.get("global");
            if ((global === null || global === void 0 ? void 0 : global.enablePasskeys) != null) {
                yield helper.setToGlobal(bw_USER_ENABLE_PASSKEYS, global.enablePasskeys);
                global === null || global === void 0 ? true : delete global.enablePasskeys;
                yield helper.set("global", global);
            }
        });
    }
    rollback(helper) {
        return bw_17_move_enable_passkeys_to_state_providers_awaiter(this, void 0, void 0, function* () {
            let global = yield helper.get("global");
            const globalEnablePasskeys = yield helper.getFromGlobal(bw_USER_ENABLE_PASSKEYS);
            if (globalEnablePasskeys != null) {
                global = Object.assign(global !== null && global !== void 0 ? global : {}, { enablePasskeys: globalEnablePasskeys });
                yield helper.set("global", global);
                yield helper.setToGlobal(bw_USER_ENABLE_PASSKEYS, undefined);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/18-move-autofill-settings-to-state-providers.ts
var bw_18_move_autofill_settings_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// FIXME: Remove when updating file. Eslint update
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const bw_18_move_autofill_settings_to_state_providers_AutofillOverlayVisibility = {
    Off: 0,
    OnButtonClick: 1,
    OnFieldFocus: 2,
};
const bw_autofillSettingsStateDefinition = {
    stateDefinition: {
        name: "autofillSettings",
    },
};
class bw_AutofillSettingsKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_18_move_autofill_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
            // global state (e.g. "autoFillOverlayVisibility -> inlineMenuVisibility")
            const globalState = yield helper.get("global");
            if ((globalState === null || globalState === void 0 ? void 0 : globalState.autoFillOverlayVisibility) != null) {
                yield helper.setToGlobal({
                    stateDefinition: {
                        name: "autofillSettingsLocal",
                    },
                    key: "inlineMenuVisibility",
                }, globalState.autoFillOverlayVisibility);
                // delete `autoFillOverlayVisibility` from state global
                delete globalState.autoFillOverlayVisibility;
                yield helper.set("global", globalState);
            }
            // account state (e.g. account settings -> state provider framework keys)
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            // migrate account state
            function migrateAccount(userId, account) {
                return bw_18_move_autofill_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    let updateAccount = false;
                    const accountSettings = account === null || account === void 0 ? void 0 : account.settings;
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.autoFillOnPageLoadDefault) != null) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoadDefault" }), accountSettings.autoFillOnPageLoadDefault);
                        delete account.settings.autoFillOnPageLoadDefault;
                        updateAccount = true;
                    }
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.enableAutoFillOnPageLoad) != null) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoad" }), accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.enableAutoFillOnPageLoad);
                        delete account.settings.enableAutoFillOnPageLoad;
                        updateAccount = true;
                    }
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.dismissedAutoFillOnPageLoadCallout) != null) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoadCalloutIsDismissed" }), accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.dismissedAutoFillOnPageLoadCallout);
                        delete account.settings.dismissedAutoFillOnPageLoadCallout;
                        updateAccount = true;
                    }
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.disableAutoTotpCopy) != null) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autoCopyTotp" }), 
                        // invert the value to match the new naming convention
                        !(accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.disableAutoTotpCopy));
                        delete account.settings.disableAutoTotpCopy;
                        updateAccount = true;
                    }
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.activateAutoFillOnPageLoadFromPolicy) != null) {
                        yield helper.setToUser(userId, {
                            stateDefinition: {
                                name: "autofillSettingsLocal",
                            },
                            key: "activateAutofillOnPageLoadFromPolicy",
                        }, accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.activateAutoFillOnPageLoadFromPolicy);
                        delete account.settings.activateAutoFillOnPageLoadFromPolicy;
                        updateAccount = true;
                    }
                    if (updateAccount) {
                        // update the state account settings with the migrated values deleted
                        yield helper.set(userId, account);
                    }
                });
            }
        });
    }
    rollback(helper) {
        return bw_18_move_autofill_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
            // global state (e.g. "inlineMenuVisibility -> autoFillOverlayVisibility")
            const globalState = (yield helper.get("global")) || {};
            const inlineMenuVisibility = yield helper.getFromGlobal({
                stateDefinition: {
                    name: "autofillSettingsLocal",
                },
                key: "inlineMenuVisibility",
            });
            if (inlineMenuVisibility) {
                yield helper.set("global", Object.assign(Object.assign({}, globalState), { autoFillOverlayVisibility: inlineMenuVisibility }));
                // remove the global state provider framework key for `inlineMenuVisibility`
                yield helper.setToGlobal({
                    stateDefinition: {
                        name: "autofillSettingsLocal",
                    },
                    key: "inlineMenuVisibility",
                }, null);
            }
            // account state (e.g. state provider framework keys -> account settings)
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
            // rollback account state
            function rollbackAccount(userId, account) {
                return bw_18_move_autofill_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    let updateAccount = false;
                    let settings = (account === null || account === void 0 ? void 0 : account.settings) || {};
                    const autoFillOnPageLoadDefault = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoadDefault" }));
                    const enableAutoFillOnPageLoad = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoad" }));
                    const dismissedAutoFillOnPageLoadCallout = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoadCalloutIsDismissed" }));
                    const autoCopyTotp = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autoCopyTotp" }));
                    const activateAutoFillOnPageLoadFromPolicy = yield helper.getFromUser(userId, {
                        stateDefinition: {
                            name: "autofillSettingsLocal",
                        },
                        key: "activateAutofillOnPageLoadFromPolicy",
                    });
                    // update new settings and remove the account state provider framework keys for the rolled back values
                    if (autoFillOnPageLoadDefault != null) {
                        settings = Object.assign(Object.assign({}, settings), { autoFillOnPageLoadDefault });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoadDefault" }), null);
                        updateAccount = true;
                    }
                    if (enableAutoFillOnPageLoad != null) {
                        settings = Object.assign(Object.assign({}, settings), { enableAutoFillOnPageLoad });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoad" }), null);
                        updateAccount = true;
                    }
                    if (dismissedAutoFillOnPageLoadCallout != null) {
                        settings = Object.assign(Object.assign({}, settings), { dismissedAutoFillOnPageLoadCallout });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autofillOnPageLoadCalloutIsDismissed" }), null);
                        updateAccount = true;
                    }
                    if (autoCopyTotp != null) {
                        // invert the value to match the new naming convention
                        settings = Object.assign(Object.assign({}, settings), { disableAutoTotpCopy: !autoCopyTotp });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsStateDefinition), { key: "autoCopyTotp" }), null);
                        updateAccount = true;
                    }
                    if (activateAutoFillOnPageLoadFromPolicy != null) {
                        settings = Object.assign(Object.assign({}, settings), { activateAutoFillOnPageLoadFromPolicy });
                        yield helper.setToUser(userId, {
                            stateDefinition: {
                                name: "autofillSettingsLocal",
                            },
                            key: "activateAutofillOnPageLoadFromPolicy",
                        }, null);
                        updateAccount = true;
                    }
                    if (updateAccount) {
                        // commit updated settings to state
                        yield helper.set(userId, Object.assign(Object.assign({}, account), { settings }));
                    }
                });
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/19-migrate-require-password-on-start.ts
var bw_19_migrate_require_password_on_start_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// Biometric text, no auto prompt text, fingerprint validated, and prompt cancelled are refreshed on every app start, so we don't need to migrate them
const bw_19_migrate_require_password_on_start_REQUIRE_PASSWORD_ON_START = {
    key: "requirePasswordOnStart",
    stateDefinition: { name: "biometricSettings" },
};
class bw_RequirePasswordOnStartMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_19_migrate_require_password_on_start_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_19_migrate_require_password_on_start_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b;
                // Move account data
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.requirePasswordOnStart) != null) {
                    yield helper.setToUser(userId, bw_19_migrate_require_password_on_start_REQUIRE_PASSWORD_ON_START, account.settings.requirePasswordOnStart);
                    // Delete old account data
                    delete account.settings.requirePasswordOnStart;
                    yield helper.set(userId, account);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_19_migrate_require_password_on_start_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_19_migrate_require_password_on_start_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const requirePassword = yield helper.getFromUser(userId, bw_19_migrate_require_password_on_start_REQUIRE_PASSWORD_ON_START);
                    if (requirePassword) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.settings) !== null && _a !== void 0 ? _a : (account.settings = {});
                        account.settings.requirePasswordOnStart = requirePassword;
                        yield helper.setToUser(userId, bw_19_migrate_require_password_on_start_REQUIRE_PASSWORD_ON_START, null);
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/20-move-private-key-to-state-providers.ts
var bw_20_move_private_key_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_20_move_private_key_to_state_providers_USER_ENCRYPTED_PRIVATE_KEY = {
    key: "privateKey",
    stateDefinition: {
        name: "crypto",
    },
};
class bw_PrivateKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_20_move_private_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_20_move_private_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.privateKey) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_20_move_private_key_to_state_providers_USER_ENCRYPTED_PRIVATE_KEY, value);
                        delete account.keys.privateKey;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_20_move_private_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_20_move_private_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_20_move_private_key_to_state_providers_USER_ENCRYPTED_PRIVATE_KEY);
                    if (account && value) {
                        account.keys = Object.assign((_a = account.keys) !== null && _a !== void 0 ? _a : {}, {
                            privateKey: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_20_move_private_key_to_state_providers_USER_ENCRYPTED_PRIVATE_KEY, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/21-move-collections-state-to-state-provider.ts
var bw_21_move_collections_state_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_USER_ENCRYPTED_COLLECTIONS = {
    key: "collections",
    stateDefinition: {
        name: "collection",
    },
};
class bw_CollectionMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_21_move_collections_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_21_move_collections_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.collections) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_USER_ENCRYPTED_COLLECTIONS, value);
                        delete account.data.collections;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_21_move_collections_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_21_move_collections_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_USER_ENCRYPTED_COLLECTIONS);
                    if (account) {
                        account.data = Object.assign((_a = account.data) !== null && _a !== void 0 ? _a : {}, {
                            collections: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_USER_ENCRYPTED_COLLECTIONS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/22-move-collapsed-groupings-to-state-provider.ts
var bw_22_move_collapsed_groupings_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_COLLAPSED_GROUPINGS = {
    key: "collapsedGroupings",
    stateDefinition: {
        name: "vaultFilter",
    },
};
class bw_CollapsedGroupingsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_22_move_collapsed_groupings_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_22_move_collapsed_groupings_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.collapsedGroupings;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_COLLAPSED_GROUPINGS, value);
                        delete account.settings.collapsedGroupings;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_22_move_collapsed_groupings_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_22_move_collapsed_groupings_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_COLLAPSED_GROUPINGS);
                    if (account) {
                        account.settings = Object.assign((_a = account.settings) !== null && _a !== void 0 ? _a : {}, {
                            collapsedGroupings: value,
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_COLLAPSED_GROUPINGS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/23-move-biometric-prompts-to-state-providers.ts
var bw_23_move_biometric_prompts_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// prompt cancelled is refreshed on every app start/quit/unlock, so we don't need to migrate it
const bw_DISMISSED_BIOMETRIC_REQUIRE_PASSWORD_ON_START_CALLOUT = {
    key: "dismissedBiometricRequirePasswordOnStartCallout",
    stateDefinition: { name: "biometricSettings" },
};
const bw_23_move_biometric_prompts_to_state_providers_PROMPT_AUTOMATICALLY = {
    key: "promptAutomatically",
    stateDefinition: { name: "biometricSettings" },
};
class bw_MoveBiometricPromptsToStateProviders extends bw_Migrator {
    migrate(helper) {
        return bw_23_move_biometric_prompts_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_23_move_biometric_prompts_to_state_providers_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c, _d, _e;
                if (account == null) {
                    return;
                }
                // Move account data
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.dismissedBiometricRequirePasswordOnStartCallout) != null) {
                    yield helper.setToUser(userId, bw_DISMISSED_BIOMETRIC_REQUIRE_PASSWORD_ON_START_CALLOUT, account.settings.dismissedBiometricRequirePasswordOnStartCallout);
                }
                if (((_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? void 0 : _c.disableAutoBiometricsPrompt) != null) {
                    yield helper.setToUser(userId, bw_23_move_biometric_prompts_to_state_providers_PROMPT_AUTOMATICALLY, !account.settings.disableAutoBiometricsPrompt);
                }
                // Delete old account data
                (_d = account === null || account === void 0 ? void 0 : account.settings) === null || _d === void 0 ? true : delete _d.dismissedBiometricRequirePasswordOnStartCallout;
                (_e = account === null || account === void 0 ? void 0 : account.settings) === null || _e === void 0 ? true : delete _e.disableAutoBiometricsPrompt;
                yield helper.set(userId, account);
            })));
        });
    }
    rollback(helper) {
        return bw_23_move_biometric_prompts_to_state_providers_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_23_move_biometric_prompts_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    let updatedAccount = false;
                    const userDismissed = yield helper.getFromUser(userId, bw_DISMISSED_BIOMETRIC_REQUIRE_PASSWORD_ON_START_CALLOUT);
                    if (userDismissed) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.settings) !== null && _a !== void 0 ? _a : (account.settings = {});
                        updatedAccount = true;
                        account.settings.dismissedBiometricRequirePasswordOnStartCallout = userDismissed;
                        yield helper.setToUser(userId, bw_DISMISSED_BIOMETRIC_REQUIRE_PASSWORD_ON_START_CALLOUT, null);
                    }
                    const userPromptAutomatically = yield helper.getFromUser(userId, bw_23_move_biometric_prompts_to_state_providers_PROMPT_AUTOMATICALLY);
                    if (userPromptAutomatically != null) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_b = account.settings) !== null && _b !== void 0 ? _b : (account.settings = {});
                        updatedAccount = true;
                        account.settings.disableAutoBiometricsPrompt = !userPromptAutomatically;
                        yield helper.setToUser(userId, bw_23_move_biometric_prompts_to_state_providers_PROMPT_AUTOMATICALLY, null);
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/24-move-sm-onboarding-key-to-state-providers.ts
var bw_24_move_sm_onboarding_key_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_SM_ONBOARDING_TASKS = {
    key: "tasks",
    stateDefinition: { name: "smOnboarding" },
};
class bw_SmOnboardingTasksMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_24_move_sm_onboarding_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_24_move_sm_onboarding_key_to_state_providers_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b;
                // Move account data
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.smOnboardingTasks) != null) {
                    yield helper.setToUser(userId, bw_SM_ONBOARDING_TASKS, account.settings.smOnboardingTasks);
                    // Delete old account data
                    delete account.settings.smOnboardingTasks;
                    yield helper.set(userId, account);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_24_move_sm_onboarding_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_24_move_sm_onboarding_key_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const smOnboardingTasks = yield helper.getFromUser(userId, bw_SM_ONBOARDING_TASKS);
                    if (smOnboardingTasks) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.settings) !== null && _a !== void 0 ? _a : (account.settings = {});
                        account.settings.smOnboardingTasks = smOnboardingTasks;
                        yield helper.setToUser(userId, bw_SM_ONBOARDING_TASKS, null);
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/25-move-clear-clipboard-to-autofill-settings-state-provider.ts
var bw_25_move_clear_clipboard_to_autofill_settings_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// FIXME: Remove when updating file. Eslint update
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const bw_25_move_clear_clipboard_to_autofill_settings_state_provider_ClearClipboardDelay = {
    Never: null,
    TenSeconds: 10,
    TwentySeconds: 20,
    ThirtySeconds: 30,
    OneMinute: 60,
    TwoMinutes: 120,
    FiveMinutes: 300,
};
const bw_autofillSettingsLocalStateDefinition = {
    stateDefinition: {
        name: "autofillSettingsLocal",
    },
};
class bw_ClearClipboardDelayMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_25_move_clear_clipboard_to_autofill_settings_state_provider_awaiter(this, void 0, void 0, function* () {
            // account state (e.g. account settings -> state provider framework keys)
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            // migrate account state
            function migrateAccount(userId, account) {
                return bw_25_move_clear_clipboard_to_autofill_settings_state_provider_awaiter(this, void 0, void 0, function* () {
                    const accountSettings = account === null || account === void 0 ? void 0 : account.settings;
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.clearClipboard) !== undefined) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsLocalStateDefinition), { key: "clearClipboardDelay" }), accountSettings.clearClipboard);
                        delete account.settings.clearClipboard;
                        // update the state account settings with the migrated values deleted
                        yield helper.set(userId, account);
                    }
                });
            }
        });
    }
    rollback(helper) {
        return bw_25_move_clear_clipboard_to_autofill_settings_state_provider_awaiter(this, void 0, void 0, function* () {
            // account state (e.g. state provider framework keys -> account settings)
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
            // rollback account state
            function rollbackAccount(userId, account) {
                return bw_25_move_clear_clipboard_to_autofill_settings_state_provider_awaiter(this, void 0, void 0, function* () {
                    let settings = (account === null || account === void 0 ? void 0 : account.settings) || {};
                    const clearClipboardDelay = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsLocalStateDefinition), { key: "clearClipboardDelay" }));
                    // update new settings and remove the account state provider framework keys for the rolled back values
                    if (clearClipboardDelay !== undefined) {
                        settings = Object.assign(Object.assign({}, settings), { clearClipboard: clearClipboardDelay });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_autofillSettingsLocalStateDefinition), { key: "clearClipboardDelay" }), null);
                        // commit updated settings to state
                        yield helper.set(userId, Object.assign(Object.assign({}, account), { settings }));
                    }
                });
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/26-revert-move-last-sync-to-state-provider.ts
var bw_26_revert_move_last_sync_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_26_revert_move_last_sync_to_state_provider_LAST_SYNC_KEY = {
    key: "lastSync",
    stateDefinition: {
        name: "sync",
    },
};
class bw_RevertLastSyncMigrator extends bw_Migrator {
    rollback(helper) {
        return bw_26_revert_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_26_revert_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.lastSync;
                    yield helper.setToUser(userId, bw_26_revert_move_last_sync_to_state_provider_LAST_SYNC_KEY, value !== null && value !== void 0 ? value : null);
                    if (value != null) {
                        delete account.profile.lastSync;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
    migrate(helper) {
        return bw_26_revert_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_26_revert_move_last_sync_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_26_revert_move_last_sync_to_state_provider_LAST_SYNC_KEY);
                    if (account) {
                        account.profile = Object.assign((_a = account.profile) !== null && _a !== void 0 ? _a : {}, {
                            lastSync: value,
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_26_revert_move_last_sync_to_state_provider_LAST_SYNC_KEY, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/27-move-badge-settings-to-state-providers.ts
var bw_27_move_badge_settings_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_enableBadgeCounterKeyDefinition = {
    stateDefinition: {
        name: "badgeSettings",
    },
    key: "enableBadgeCounter",
};
class bw_BadgeSettingsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_27_move_badge_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
            // account state (e.g. account settings -> state provider framework keys)
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            // migrate account state
            function migrateAccount(userId, account) {
                return bw_27_move_badge_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    const accountSettings = account === null || account === void 0 ? void 0 : account.settings;
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.disableBadgeCounter) != undefined) {
                        yield helper.setToUser(userId, bw_enableBadgeCounterKeyDefinition, !accountSettings.disableBadgeCounter);
                        delete account.settings.disableBadgeCounter;
                        // update the state account settings with the migrated values deleted
                        yield helper.set(userId, account);
                    }
                });
            }
        });
    }
    rollback(helper) {
        return bw_27_move_badge_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
            // account state (e.g. state provider framework keys -> account settings)
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
            // rollback account state
            function rollbackAccount(userId, account) {
                return bw_27_move_badge_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    let settings = (account === null || account === void 0 ? void 0 : account.settings) || {};
                    const enableBadgeCounter = yield helper.getFromUser(userId, bw_enableBadgeCounterKeyDefinition);
                    // update new settings and remove the account state provider framework keys for the rolled back values
                    if (enableBadgeCounter != undefined) {
                        settings = Object.assign(Object.assign({}, settings), { disableBadgeCounter: !enableBadgeCounter });
                        yield helper.setToUser(userId, bw_enableBadgeCounterKeyDefinition, null);
                        // commit updated settings to state
                        yield helper.set(userId, Object.assign(Object.assign({}, account), { settings }));
                    }
                });
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/28-move-biometric-unlock-to-state-providers.ts
var bw_28_move_biometric_unlock_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_28_move_biometric_unlock_to_state_providers_BIOMETRIC_UNLOCK_ENABLED = {
    key: "biometricUnlockEnabled",
    stateDefinition: { name: "biometricSettings" },
};
class bw_MoveBiometricUnlockToStateProviders extends bw_Migrator {
    migrate(helper) {
        return bw_28_move_biometric_unlock_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_28_move_biometric_unlock_to_state_providers_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c;
                if (account == null) {
                    return;
                }
                // Move account data
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.biometricUnlock) != null) {
                    yield helper.setToUser(userId, bw_28_move_biometric_unlock_to_state_providers_BIOMETRIC_UNLOCK_ENABLED, account.settings.biometricUnlock);
                }
                // Delete old account data
                (_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? true : delete _c.biometricUnlock;
                yield helper.set(userId, account);
            })));
        });
    }
    rollback(helper) {
        return bw_28_move_biometric_unlock_to_state_providers_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_28_move_biometric_unlock_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const biometricUnlock = yield helper.getFromUser(userId, bw_28_move_biometric_unlock_to_state_providers_BIOMETRIC_UNLOCK_ENABLED);
                    if (biometricUnlock != null) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.settings) !== null && _a !== void 0 ? _a : (account.settings = {});
                        account.settings.biometricUnlock = biometricUnlock;
                        yield helper.setToUser(userId, bw_28_move_biometric_unlock_to_state_providers_BIOMETRIC_UNLOCK_ENABLED, null);
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/29-move-user-notification-settings-to-state-provider.ts
var bw_29_move_user_notification_settings_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_UserNotificationSettingsKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_29_move_user_notification_settings_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const globalState = yield helper.get("global");
            // disableAddLoginNotification -> enableAddedLoginPrompt
            if ((globalState === null || globalState === void 0 ? void 0 : globalState.disableAddLoginNotification) != null) {
                yield helper.setToGlobal({
                    stateDefinition: {
                        name: "userNotificationSettings",
                    },
                    key: "enableAddedLoginPrompt",
                }, !globalState.disableAddLoginNotification);
                // delete `disableAddLoginNotification` from state global
                delete globalState.disableAddLoginNotification;
                yield helper.set("global", globalState);
            }
            // disableChangedPasswordNotification -> enableChangedPasswordPrompt
            if ((globalState === null || globalState === void 0 ? void 0 : globalState.disableChangedPasswordNotification) != null) {
                yield helper.setToGlobal({
                    stateDefinition: {
                        name: "userNotificationSettings",
                    },
                    key: "enableChangedPasswordPrompt",
                }, !globalState.disableChangedPasswordNotification);
                // delete `disableChangedPasswordNotification` from state global
                delete globalState.disableChangedPasswordNotification;
                yield helper.set("global", globalState);
            }
        });
    }
    rollback(helper) {
        return bw_29_move_user_notification_settings_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const globalState = (yield helper.get("global")) || {};
            const enableAddedLoginPrompt = yield helper.getFromGlobal({
                stateDefinition: {
                    name: "userNotificationSettings",
                },
                key: "enableAddedLoginPrompt",
            });
            const enableChangedPasswordPrompt = yield helper.getFromGlobal({
                stateDefinition: {
                    name: "userNotificationSettings",
                },
                key: "enableChangedPasswordPrompt",
            });
            // enableAddedLoginPrompt -> disableAddLoginNotification
            if (enableAddedLoginPrompt) {
                yield helper.set("global", Object.assign(Object.assign({}, globalState), { disableAddLoginNotification: !enableAddedLoginPrompt }));
                // remove the global state provider framework key for `enableAddedLoginPrompt`
                yield helper.setToGlobal({
                    stateDefinition: {
                        name: "userNotificationSettings",
                    },
                    key: "enableAddedLoginPrompt",
                }, null);
            }
            // enableChangedPasswordPrompt -> disableChangedPasswordNotification
            if (enableChangedPasswordPrompt) {
                yield helper.set("global", Object.assign(Object.assign({}, globalState), { disableChangedPasswordNotification: !enableChangedPasswordPrompt }));
                // remove the global state provider framework key for `enableChangedPasswordPrompt`
                yield helper.setToGlobal({
                    stateDefinition: {
                        name: "userNotificationSettings",
                    },
                    key: "enableChangedPasswordPrompt",
                }, null);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/30-move-policy-state-to-state-provider.ts
var bw_30_move_policy_state_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

var bw_30_move_policy_state_to_state_provider_PolicyType;
(function (PolicyType) {
    PolicyType[PolicyType["TwoFactorAuthentication"] = 0] = "TwoFactorAuthentication";
    PolicyType[PolicyType["MasterPassword"] = 1] = "MasterPassword";
    PolicyType[PolicyType["PasswordGenerator"] = 2] = "PasswordGenerator";
    PolicyType[PolicyType["SingleOrg"] = 3] = "SingleOrg";
    PolicyType[PolicyType["RequireSso"] = 4] = "RequireSso";
    PolicyType[PolicyType["PersonalOwnership"] = 5] = "PersonalOwnership";
    PolicyType[PolicyType["DisableSend"] = 6] = "DisableSend";
    PolicyType[PolicyType["SendOptions"] = 7] = "SendOptions";
    PolicyType[PolicyType["ResetPassword"] = 8] = "ResetPassword";
    PolicyType[PolicyType["MaximumVaultTimeout"] = 9] = "MaximumVaultTimeout";
    PolicyType[PolicyType["DisablePersonalVaultExport"] = 10] = "DisablePersonalVaultExport";
    PolicyType[PolicyType["ActivateAutofill"] = 11] = "ActivateAutofill";
})(bw_30_move_policy_state_to_state_provider_PolicyType || (bw_30_move_policy_state_to_state_provider_PolicyType = {}));
const bw_POLICIES_KEY = {
    key: "policies",
    stateDefinition: {
        name: "policies",
    },
};
class bw_PolicyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_30_move_policy_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_30_move_policy_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.policies) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_POLICIES_KEY, value);
                        delete account.data.policies;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all(accounts.map(({ userId, account }) => migrateAccount(userId, account)));
        });
    }
    rollback(helper) {
        return bw_30_move_policy_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_30_move_policy_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_POLICIES_KEY);
                    if (account) {
                        account.data = Object.assign((_a = account.data) !== null && _a !== void 0 ? _a : {}, {
                            policies: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_POLICIES_KEY, null);
                });
            }
            yield Promise.all(accounts.map(({ userId, account }) => rollbackAccount(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/31-move-enable-context-menu-to-autofill-settings-state-provider.ts
var bw_31_move_enable_context_menu_to_autofill_settings_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_enableContextMenuKeyDefinition = {
    stateDefinition: {
        name: "autofillSettings",
    },
    key: "enableContextMenu",
};
class bw_EnableContextMenuMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_31_move_enable_context_menu_to_autofill_settings_state_provider_awaiter(this, void 0, void 0, function* () {
            const globalState = yield helper.get("global");
            // disableContextMenuItem -> enableContextMenu
            if ((globalState === null || globalState === void 0 ? void 0 : globalState.disableContextMenuItem) != null) {
                yield helper.setToGlobal(bw_enableContextMenuKeyDefinition, !globalState.disableContextMenuItem);
                // delete `disableContextMenuItem` from state global
                delete globalState.disableContextMenuItem;
                yield helper.set("global", globalState);
            }
        });
    }
    rollback(helper) {
        return bw_31_move_enable_context_menu_to_autofill_settings_state_provider_awaiter(this, void 0, void 0, function* () {
            const globalState = (yield helper.get("global")) || {};
            const enableContextMenu = yield helper.getFromGlobal(bw_enableContextMenuKeyDefinition);
            // enableContextMenu -> disableContextMenuItem
            if (enableContextMenu != null) {
                yield helper.set("global", Object.assign(Object.assign({}, globalState), { disableContextMenuItem: !enableContextMenu }));
                // remove the global state provider framework key for `enableContextMenu`
                yield helper.setToGlobal(bw_enableContextMenuKeyDefinition, null);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/32-move-preferred-language.ts
var bw_32_move_preferred_language_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_LOCALE_KEY = {
    key: "locale",
    stateDefinition: {
        name: "translation",
    },
};
class bw_PreferredLanguageMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_32_move_preferred_language_awaiter(this, void 0, void 0, function* () {
            // global state
            const global = yield helper.get("global");
            if (!(global === null || global === void 0 ? void 0 : global.locale)) {
                return;
            }
            yield helper.setToGlobal(bw_LOCALE_KEY, global.locale);
            delete global.locale;
            yield helper.set("global", global);
        });
    }
    rollback(helper) {
        return bw_32_move_preferred_language_awaiter(this, void 0, void 0, function* () {
            var _a;
            const locale = yield helper.getFromGlobal(bw_LOCALE_KEY);
            if (!locale) {
                return;
            }
            const global = (_a = (yield helper.get("global"))) !== null && _a !== void 0 ? _a : {};
            global.locale = locale;
            yield helper.set("global", global);
            yield helper.setToGlobal(bw_LOCALE_KEY, null);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/33-move-app-id-to-state-providers.ts
var bw_33_move_app_id_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_APP_ID_STORAGE_KEY = "appId";
const bw_ANONYMOUS_APP_ID_STORAGE_KEY = "anonymousAppId";
const bw_33_move_app_id_to_state_providers_APP_ID_KEY = {
    key: bw_APP_ID_STORAGE_KEY,
    stateDefinition: { name: "applicationId" },
};
const bw_33_move_app_id_to_state_providers_ANONYMOUS_APP_ID_KEY = {
    key: bw_ANONYMOUS_APP_ID_STORAGE_KEY,
    stateDefinition: { name: "applicationId" },
};
class bw_AppIdMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_33_move_app_id_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const appId = yield helper.get(bw_APP_ID_STORAGE_KEY);
            const anonymousAppId = yield helper.get(bw_ANONYMOUS_APP_ID_STORAGE_KEY);
            if (appId != null) {
                yield helper.setToGlobal(bw_33_move_app_id_to_state_providers_APP_ID_KEY, appId);
                yield helper.set(bw_APP_ID_STORAGE_KEY, null);
            }
            if (anonymousAppId != null) {
                yield helper.setToGlobal(bw_33_move_app_id_to_state_providers_ANONYMOUS_APP_ID_KEY, anonymousAppId);
                yield helper.set(bw_ANONYMOUS_APP_ID_STORAGE_KEY, null);
            }
        });
    }
    rollback(helper) {
        return bw_33_move_app_id_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const appId = yield helper.getFromGlobal(bw_33_move_app_id_to_state_providers_APP_ID_KEY);
            const anonymousAppId = yield helper.getFromGlobal(bw_33_move_app_id_to_state_providers_ANONYMOUS_APP_ID_KEY);
            if (appId != null) {
                yield helper.set(bw_APP_ID_STORAGE_KEY, appId);
                yield helper.setToGlobal(bw_33_move_app_id_to_state_providers_APP_ID_KEY, null);
            }
            if (anonymousAppId != null) {
                yield helper.set(bw_ANONYMOUS_APP_ID_STORAGE_KEY, anonymousAppId);
                yield helper.setToGlobal(bw_33_move_app_id_to_state_providers_ANONYMOUS_APP_ID_KEY, null);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/34-move-domain-settings-to-state-providers.ts
var bw_34_move_domain_settings_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// FIXME: Remove when updating file. Eslint update
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const bw_34_move_domain_settings_to_state_providers_UriMatchStrategy = {
    Domain: 0,
    Host: 1,
    StartsWith: 2,
    Exact: 3,
    RegularExpression: 4,
    Never: 5,
};
const bw_defaultUriMatchStrategyDefinition = {
    stateDefinition: {
        name: "domainSettings",
    },
    key: "defaultUriMatchStrategy",
};
const bw_equivalentDomainsDefinition = {
    stateDefinition: {
        name: "domainSettings",
    },
    key: "equivalentDomains",
};
const bw_neverDomainsDefinition = {
    stateDefinition: {
        name: "domainSettings",
    },
    key: "neverDomains",
};
class bw_DomainSettingsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_34_move_domain_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
            let updateAccount = false;
            // global state ("neverDomains")
            const globalState = yield helper.get("global");
            if ((globalState === null || globalState === void 0 ? void 0 : globalState.neverDomains) != null) {
                yield helper.setToGlobal(bw_neverDomainsDefinition, globalState.neverDomains);
                // delete `neverDomains` from state global
                delete globalState.neverDomains;
                yield helper.set("global", globalState);
            }
            // account state ("defaultUriMatch" and "settings.equivalentDomains")
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            // migrate account state
            function migrateAccount(userId, account) {
                return bw_34_move_domain_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const accountSettings = account === null || account === void 0 ? void 0 : account.settings;
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.defaultUriMatch) != undefined) {
                        yield helper.setToUser(userId, bw_defaultUriMatchStrategyDefinition, accountSettings.defaultUriMatch);
                        delete account.settings.defaultUriMatch;
                        updateAccount = true;
                    }
                    if (((_a = accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.settings) === null || _a === void 0 ? void 0 : _a.equivalentDomains) != undefined) {
                        yield helper.setToUser(userId, bw_equivalentDomainsDefinition, accountSettings.settings.equivalentDomains);
                        delete account.settings.settings.equivalentDomains;
                        delete account.settings.settings;
                        updateAccount = true;
                    }
                    if (updateAccount) {
                        // update the state account settings with the migrated values deleted
                        yield helper.set(userId, account);
                    }
                });
            }
        });
    }
    rollback(helper) {
        return bw_34_move_domain_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
            let updateAccount = false;
            // global state ("neverDomains")
            const globalState = (yield helper.get("global")) || {};
            const neverDomains = yield helper.getFromGlobal(bw_neverDomainsDefinition);
            if (neverDomains != null) {
                yield helper.set("global", Object.assign(Object.assign({}, globalState), { neverDomains: neverDomains }));
                // remove the global state provider framework key for `neverDomains`
                yield helper.setToGlobal(bw_neverDomainsDefinition, null);
            }
            // account state ("defaultUriMatchStrategy" and "equivalentDomains")
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
            // rollback account state
            function rollbackAccount(userId, account) {
                return bw_34_move_domain_settings_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    let settings = (account === null || account === void 0 ? void 0 : account.settings) || {};
                    const defaultUriMatchStrategy = yield helper.getFromUser(userId, bw_defaultUriMatchStrategyDefinition);
                    const equivalentDomains = yield helper.getFromUser(userId, bw_equivalentDomainsDefinition);
                    // update new settings and remove the account state provider framework keys for the rolled back values
                    if (defaultUriMatchStrategy != null) {
                        settings = Object.assign(Object.assign({}, settings), { defaultUriMatch: defaultUriMatchStrategy });
                        yield helper.setToUser(userId, bw_defaultUriMatchStrategyDefinition, null);
                        updateAccount = true;
                    }
                    if (equivalentDomains != null) {
                        settings = Object.assign(Object.assign({}, settings), { settings: { equivalentDomains } });
                        yield helper.setToUser(userId, bw_equivalentDomainsDefinition, null);
                        updateAccount = true;
                    }
                    // commit updated settings to state
                    if (updateAccount) {
                        yield helper.set(userId, Object.assign(Object.assign({}, account), { settings }));
                    }
                });
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/35-move-theme-to-state-providers.ts
var bw_35_move_theme_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_THEME_SELECTION = {
    key: "selection",
    stateDefinition: { name: "theming" },
};
class bw_MoveThemeToStateProviderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_35_move_theme_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const legacyGlobalState = yield helper.get("global");
            const theme = legacyGlobalState === null || legacyGlobalState === void 0 ? void 0 : legacyGlobalState.theme;
            if (theme != null) {
                yield helper.setToGlobal(bw_THEME_SELECTION, theme);
                delete legacyGlobalState.theme;
                yield helper.set("global", legacyGlobalState);
            }
        });
    }
    rollback(helper) {
        return bw_35_move_theme_to_state_providers_awaiter(this, void 0, void 0, function* () {
            var _a;
            const theme = yield helper.getFromGlobal(bw_THEME_SELECTION);
            if (theme != null) {
                const legacyGlobal = (_a = (yield helper.get("global"))) !== null && _a !== void 0 ? _a : {};
                legacyGlobal.theme = theme;
                yield helper.set("global", legacyGlobal);
                yield helper.removeFromGlobal(bw_THEME_SELECTION);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/36-move-show-card-and-identity-to-state-provider.ts
var bw_36_move_show_card_and_identity_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_vaultSettingsStateDefinition = {
    stateDefinition: {
        name: "vaultSettings",
    },
};
class bw_VaultSettingsKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_36_move_show_card_and_identity_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            function migrateAccount(userId, account) {
                return bw_36_move_show_card_and_identity_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    let updateAccount = false;
                    const accountSettings = account === null || account === void 0 ? void 0 : account.settings;
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.dontShowCardsCurrentTab) != null) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_vaultSettingsStateDefinition), { key: "showCardsCurrentTab" }), !accountSettings.dontShowCardsCurrentTab);
                        delete account.settings.dontShowCardsCurrentTab;
                        updateAccount = true;
                    }
                    if ((accountSettings === null || accountSettings === void 0 ? void 0 : accountSettings.dontShowIdentitiesCurrentTab) != null) {
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_vaultSettingsStateDefinition), { key: "showIdentitiesCurrentTab" }), !accountSettings.dontShowIdentitiesCurrentTab);
                        delete account.settings.dontShowIdentitiesCurrentTab;
                        updateAccount = true;
                    }
                    if (updateAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
        });
    }
    rollback(helper) {
        return bw_36_move_show_card_and_identity_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
            function rollbackAccount(userId, account) {
                return bw_36_move_show_card_and_identity_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    let updateAccount = false;
                    let settings = (_a = account === null || account === void 0 ? void 0 : account.settings) !== null && _a !== void 0 ? _a : {};
                    const showCardsCurrentTab = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_vaultSettingsStateDefinition), { key: "showCardsCurrentTab" }));
                    const showIdentitiesCurrentTab = yield helper.getFromUser(userId, Object.assign(Object.assign({}, bw_vaultSettingsStateDefinition), { key: "showIdentitiesCurrentTab" }));
                    if (showCardsCurrentTab != null) {
                        // invert the value to match the new naming convention
                        settings = Object.assign(Object.assign({}, settings), { dontShowCardsCurrentTab: !showCardsCurrentTab });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_vaultSettingsStateDefinition), { key: "showCardsCurrentTab" }), null);
                        updateAccount = true;
                    }
                    if (showIdentitiesCurrentTab != null) {
                        // invert the value to match the new naming convention
                        settings = Object.assign(Object.assign({}, settings), { dontShowIdentitiesCurrentTab: !showIdentitiesCurrentTab });
                        yield helper.setToUser(userId, Object.assign(Object.assign({}, bw_vaultSettingsStateDefinition), { key: "showIdentitiesCurrentTab" }), null);
                        updateAccount = true;
                    }
                    if (updateAccount) {
                        yield helper.set(userId, Object.assign(Object.assign({}, account), { settings }));
                    }
                });
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/37-move-avatar-color-to-state-providers.ts
var bw_37_move_avatar_color_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_AVATAR_COLOR_STATE = { name: "avatar" };
const bw_AVATAR_COLOR_KEY = {
    key: "avatarColor",
    stateDefinition: bw_AVATAR_COLOR_STATE,
};
class bw_AvatarColorMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_37_move_avatar_color_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_37_move_avatar_color_to_state_providers_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c;
                // Move account avatarColor
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.avatarColor) != null) {
                    yield helper.setToUser(userId, bw_AVATAR_COLOR_KEY, account.settings.avatarColor);
                    // Delete old account avatarColor property
                    (_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? true : delete _c.avatarColor;
                    yield helper.set(userId, account);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_37_move_avatar_color_to_state_providers_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_37_move_avatar_color_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    let updatedAccount = false;
                    const userAvatarColor = yield helper.getFromUser(userId, bw_AVATAR_COLOR_KEY);
                    if (userAvatarColor) {
                        if (!account) {
                            account = {};
                        }
                        updatedAccount = true;
                        account.settings.avatarColor = userAvatarColor;
                        yield helper.setToUser(userId, bw_AVATAR_COLOR_KEY, null);
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/38-migrate-token-svc-to-state-provider.ts
var bw_38_migrate_token_svc_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_38_migrate_token_svc_to_state_provider_EMAIL_TWO_FACTOR_TOKEN_RECORD_DISK_LOCAL = {
    key: "emailTwoFactorTokenRecord",
    stateDefinition: {
        name: "tokenDiskLocal",
    },
};
const bw_TOKEN_STATE_DEF_LIKE = {
    name: "token",
};
const bw_38_migrate_token_svc_to_state_provider_ACCESS_TOKEN_DISK = {
    key: "accessToken", // matches KeyDefinition.key
    stateDefinition: bw_TOKEN_STATE_DEF_LIKE,
};
const bw_38_migrate_token_svc_to_state_provider_REFRESH_TOKEN_DISK = {
    key: "refreshToken",
    stateDefinition: bw_TOKEN_STATE_DEF_LIKE,
};
const bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_ID_DISK = {
    key: "apiKeyClientId",
    stateDefinition: bw_TOKEN_STATE_DEF_LIKE,
};
const bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_SECRET_DISK = {
    key: "apiKeyClientSecret",
    stateDefinition: bw_TOKEN_STATE_DEF_LIKE,
};
class bw_TokenServiceStateProviderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_38_migrate_token_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
            // Move global data
            const globalData = yield helper.get("global");
            // Create new global record for 2FA token that we can accumulate data in
            const emailTwoFactorTokenRecord = {};
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account, globalTwoFactorToken, emailTwoFactorTokenRecord) {
                return bw_38_migrate_token_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c, _d, _e;
                    let updatedAccount = false;
                    // migrate 2FA token from global to user state
                    // Due to the existing implmentation, n users on the same device share the same global state value for 2FA token.
                    // So, we will just migrate it to all users to keep it valid for whichever was the user that set it previously.
                    // Note: don't bother migrating 2FA Token if user account or email is undefined
                    const email = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.email;
                    if (globalTwoFactorToken != undefined && account != undefined && email != undefined) {
                        emailTwoFactorTokenRecord[email] = globalTwoFactorToken;
                        // Note: don't set updatedAccount to true here as we aren't updating
                        // the legacy user state, just migrating a global state to a new user state
                    }
                    // Migrate access token
                    const existingAccessToken = (_b = account === null || account === void 0 ? void 0 : account.tokens) === null || _b === void 0 ? void 0 : _b.accessToken;
                    if (existingAccessToken != null) {
                        // Only migrate data that exists
                        if (helper.type !== "web-disk-local") {
                            // only migrate access token to session storage - never local.
                            yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_ACCESS_TOKEN_DISK, existingAccessToken);
                        }
                        delete account.tokens.accessToken;
                        updatedAccount = true;
                    }
                    // Migrate refresh token
                    const existingRefreshToken = (_c = account === null || account === void 0 ? void 0 : account.tokens) === null || _c === void 0 ? void 0 : _c.refreshToken;
                    if (existingRefreshToken != null) {
                        if (helper.type !== "web-disk-local") {
                            // only migrate refresh token to session storage - never local.
                            yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_REFRESH_TOKEN_DISK, existingRefreshToken);
                        }
                        delete account.tokens.refreshToken;
                        updatedAccount = true;
                    }
                    // Migrate API key client id
                    const existingApiKeyClientId = (_d = account === null || account === void 0 ? void 0 : account.profile) === null || _d === void 0 ? void 0 : _d.apiKeyClientId;
                    if (existingApiKeyClientId != null) {
                        if (helper.type !== "web-disk-local") {
                            // only migrate client id to session storage - never local.
                            yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_ID_DISK, existingApiKeyClientId);
                        }
                        delete account.profile.apiKeyClientId;
                        updatedAccount = true;
                    }
                    // Migrate API key client secret
                    const existingApiKeyClientSecret = (_e = account === null || account === void 0 ? void 0 : account.keys) === null || _e === void 0 ? void 0 : _e.apiKeyClientSecret;
                    if (existingApiKeyClientSecret != null) {
                        if (helper.type !== "web-disk-local") {
                            // only migrate client secret to session storage - never local.
                            yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_SECRET_DISK, existingApiKeyClientSecret);
                        }
                        delete account.keys.apiKeyClientSecret;
                        updatedAccount = true;
                    }
                    if (updatedAccount) {
                        // Save the migrated account only if it was updated
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([
                ...accounts.map(({ userId, account }) => migrateAccount(userId, account, globalData === null || globalData === void 0 ? void 0 : globalData.twoFactorToken, emailTwoFactorTokenRecord)),
            ]);
            // Save the global 2FA token record
            yield helper.setToGlobal(bw_38_migrate_token_svc_to_state_provider_EMAIL_TWO_FACTOR_TOKEN_RECORD_DISK_LOCAL, emailTwoFactorTokenRecord);
            // Delete global data
            globalData === null || globalData === void 0 ? true : delete globalData.twoFactorToken;
            yield helper.set("global", globalData);
        });
    }
    rollback(helper) {
        return bw_38_migrate_token_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
            var _a;
            const accounts = yield helper.getAccounts();
            // Since we migrated the global 2FA token to all users, we need to rollback the 2FA token for all users
            // but we only need to set it to the global state once
            // Go through accounts and find the first user that has a non-null email and 2FA token
            let migratedTwoFactorToken = null;
            for (const { account } of accounts) {
                const email = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.email;
                if (email == null) {
                    continue;
                }
                const emailTwoFactorTokenRecord = yield helper.getFromGlobal(bw_38_migrate_token_svc_to_state_provider_EMAIL_TWO_FACTOR_TOKEN_RECORD_DISK_LOCAL);
                migratedTwoFactorToken = emailTwoFactorTokenRecord[email];
                if (migratedTwoFactorToken != null) {
                    break;
                }
            }
            if (migratedTwoFactorToken != null) {
                let legacyGlobal = yield helper.get("global");
                if (!legacyGlobal) {
                    legacyGlobal = {};
                }
                legacyGlobal.twoFactorToken = migratedTwoFactorToken;
                yield helper.set("global", legacyGlobal);
            }
            // delete global 2FA token record
            yield helper.setToGlobal(bw_38_migrate_token_svc_to_state_provider_EMAIL_TWO_FACTOR_TOKEN_RECORD_DISK_LOCAL, null);
            function rollbackAccount(userId, account) {
                return bw_38_migrate_token_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    let updatedLegacyAccount = false;
                    // Rollback access token
                    const migratedAccessToken = yield helper.getFromUser(userId, bw_38_migrate_token_svc_to_state_provider_ACCESS_TOKEN_DISK);
                    if ((account === null || account === void 0 ? void 0 : account.tokens) && migratedAccessToken != null) {
                        account.tokens.accessToken = migratedAccessToken;
                        updatedLegacyAccount = true;
                    }
                    yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_ACCESS_TOKEN_DISK, null);
                    // Rollback refresh token
                    const migratedRefreshToken = yield helper.getFromUser(userId, bw_38_migrate_token_svc_to_state_provider_REFRESH_TOKEN_DISK);
                    if ((account === null || account === void 0 ? void 0 : account.tokens) && migratedRefreshToken != null) {
                        account.tokens.refreshToken = migratedRefreshToken;
                        updatedLegacyAccount = true;
                    }
                    yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_REFRESH_TOKEN_DISK, null);
                    // Rollback API key client id
                    const migratedApiKeyClientId = yield helper.getFromUser(userId, bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_ID_DISK);
                    if ((account === null || account === void 0 ? void 0 : account.profile) && migratedApiKeyClientId != null) {
                        account.profile.apiKeyClientId = migratedApiKeyClientId;
                        updatedLegacyAccount = true;
                    }
                    yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_ID_DISK, null);
                    // Rollback API key client secret
                    const migratedApiKeyClientSecret = yield helper.getFromUser(userId, bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_SECRET_DISK);
                    if ((account === null || account === void 0 ? void 0 : account.keys) && migratedApiKeyClientSecret != null) {
                        account.keys.apiKeyClientSecret = migratedApiKeyClientSecret;
                        updatedLegacyAccount = true;
                    }
                    yield helper.setToUser(userId, bw_38_migrate_token_svc_to_state_provider_API_KEY_CLIENT_SECRET_DISK, null);
                    if (updatedLegacyAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/39-move-billing-account-profile-to-state-providers.ts
var bw_39_move_billing_account_profile_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_39_move_billing_account_profile_to_state_providers_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION = {
    key: "accountProfile",
    stateDefinition: {
        name: "billing",
    },
};
class bw_MoveBillingAccountProfileMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_39_move_billing_account_profile_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            const migrateAccount = (userId, account) => bw_39_move_billing_account_profile_to_state_providers_awaiter(this, void 0, void 0, function* () {
                var _a, _b, _c, _d;
                const hasPremiumPersonally = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.hasPremiumPersonally;
                const hasPremiumFromOrganization = (_b = account === null || account === void 0 ? void 0 : account.profile) === null || _b === void 0 ? void 0 : _b.hasPremiumFromOrganization;
                if (hasPremiumPersonally != null || hasPremiumFromOrganization != null) {
                    yield helper.setToUser(userId, bw_39_move_billing_account_profile_to_state_providers_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION, {
                        hasPremiumPersonally: hasPremiumPersonally,
                        hasPremiumFromOrganization: hasPremiumFromOrganization,
                    });
                    (_c = account === null || account === void 0 ? void 0 : account.profile) === null || _c === void 0 ? true : delete _c.hasPremiumPersonally;
                    (_d = account === null || account === void 0 ? void 0 : account.profile) === null || _d === void 0 ? true : delete _d.hasPremiumFromOrganization;
                    yield helper.set(userId, account);
                }
            });
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_39_move_billing_account_profile_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            const rollbackAccount = (userId, account) => bw_39_move_billing_account_profile_to_state_providers_awaiter(this, void 0, void 0, function* () {
                var _a;
                const value = yield helper.getFromUser(userId, bw_39_move_billing_account_profile_to_state_providers_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION);
                if (account && value) {
                    account.profile = Object.assign((_a = account.profile) !== null && _a !== void 0 ? _a : {}, {
                        hasPremiumPersonally: value === null || value === void 0 ? void 0 : value.hasPremiumPersonally,
                        hasPremiumFromOrganization: value === null || value === void 0 ? void 0 : value.hasPremiumFromOrganization,
                    });
                    yield helper.set(userId, account);
                }
                yield helper.setToUser(userId, bw_39_move_billing_account_profile_to_state_providers_BILLING_ACCOUNT_PROFILE_KEY_DEFINITION, null);
            });
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/4-remove-ever-been-unlocked.ts
var bw_4_remove_ever_been_unlocked_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_RemoveEverBeenUnlockedMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_4_remove_ever_been_unlocked_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function removeEverBeenUnlocked(userId, account) {
                return bw_4_remove_ever_been_unlocked_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    if (((_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.everBeenUnlocked) != null) {
                        delete account.profile.everBeenUnlocked;
                        return helper.set(userId, account);
                    }
                });
            }
            // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
            // eslint-disable-next-line @typescript-eslint/no-floating-promises
            Promise.all(accounts.map(({ userId, account }) => removeEverBeenUnlocked(userId, account)));
        });
    }
    rollback(helper) {
        throw bw_IRREVERSIBLE;
    }
    // Override is necessary because default implementation assumes `stateVersion` at the root, but for this version
    // it is nested inside a global object.
    updateVersion(helper, direction) {
        return bw_4_remove_ever_been_unlocked_awaiter(this, void 0, void 0, function* () {
            const endVersion = direction === "up" ? this.toVersion : this.fromVersion;
            helper.currentVersion = endVersion;
            const global = (yield helper.get("global")) || {};
            yield helper.set("global", Object.assign(Object.assign({}, global), { stateVersion: endVersion }));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/40-move-organization-state-to-state-provider.ts
var bw_40_move_organization_state_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// Local declarations of `OrganizationData` and the types of it's properties.
// Duplicated to remain frozen in time when migration occurs.
var bw_40_move_organization_state_to_state_provider_OrganizationUserStatusType;
(function (OrganizationUserStatusType) {
    OrganizationUserStatusType[OrganizationUserStatusType["Invited"] = 0] = "Invited";
    OrganizationUserStatusType[OrganizationUserStatusType["Accepted"] = 1] = "Accepted";
    OrganizationUserStatusType[OrganizationUserStatusType["Confirmed"] = 2] = "Confirmed";
    OrganizationUserStatusType[OrganizationUserStatusType["Revoked"] = -1] = "Revoked";
})(bw_40_move_organization_state_to_state_provider_OrganizationUserStatusType || (bw_40_move_organization_state_to_state_provider_OrganizationUserStatusType = {}));
var bw_40_move_organization_state_to_state_provider_OrganizationUserType;
(function (OrganizationUserType) {
    OrganizationUserType[OrganizationUserType["Owner"] = 0] = "Owner";
    OrganizationUserType[OrganizationUserType["Admin"] = 1] = "Admin";
    OrganizationUserType[OrganizationUserType["User"] = 2] = "User";
    OrganizationUserType[OrganizationUserType["Manager"] = 3] = "Manager";
    OrganizationUserType[OrganizationUserType["Custom"] = 4] = "Custom";
})(bw_40_move_organization_state_to_state_provider_OrganizationUserType || (bw_40_move_organization_state_to_state_provider_OrganizationUserType = {}));
var bw_40_move_organization_state_to_state_provider_ProviderType;
(function (ProviderType) {
    ProviderType[ProviderType["Msp"] = 0] = "Msp";
    ProviderType[ProviderType["Reseller"] = 1] = "Reseller";
})(bw_40_move_organization_state_to_state_provider_ProviderType || (bw_40_move_organization_state_to_state_provider_ProviderType = {}));
var bw_40_move_organization_state_to_state_provider_ProductType;
(function (ProductType) {
    ProductType[ProductType["Free"] = 0] = "Free";
    ProductType[ProductType["Families"] = 1] = "Families";
    ProductType[ProductType["Teams"] = 2] = "Teams";
    ProductType[ProductType["Enterprise"] = 3] = "Enterprise";
    ProductType[ProductType["TeamsStarter"] = 4] = "TeamsStarter";
})(bw_40_move_organization_state_to_state_provider_ProductType || (bw_40_move_organization_state_to_state_provider_ProductType = {}));
const bw_USER_ORGANIZATIONS = {
    key: "organizations",
    stateDefinition: {
        name: "organizations",
    },
};
class bw_OrganizationMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_40_move_organization_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_40_move_organization_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.organizations;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_USER_ORGANIZATIONS, value);
                        delete account.data.organizations;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all(accounts.map(({ userId, account }) => migrateAccount(userId, account)));
        });
    }
    rollback(helper) {
        return bw_40_move_organization_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_40_move_organization_state_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_USER_ORGANIZATIONS);
                    if (account) {
                        account.data = Object.assign((_a = account.data) !== null && _a !== void 0 ? _a : {}, {
                            organizations: value,
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_USER_ORGANIZATIONS, null);
                });
            }
            yield Promise.all(accounts.map(({ userId, account }) => rollbackAccount(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/41-move-event-collection-to-state-provider.ts
var bw_41_move_event_collection_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_EVENT_COLLECTION = {
    stateDefinition: {
        name: "eventCollection",
    },
    key: "eventCollection",
};
class bw_EventCollectionMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_41_move_event_collection_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_41_move_event_collection_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.eventCollection;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_EVENT_COLLECTION, value);
                        delete account.data.eventCollection;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_41_move_event_collection_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_41_move_event_collection_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_EVENT_COLLECTION);
                    if (account) {
                        account.data = Object.assign((_a = account.data) !== null && _a !== void 0 ? _a : {}, {
                            eventCollection: value,
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_EVENT_COLLECTION, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/42-move-enable-favicon-to-domain-settings-state-provider.ts
var bw_42_move_enable_favicon_to_domain_settings_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_ShowFaviconDefinition = {
    stateDefinition: {
        name: "domainSettings",
    },
    key: "showFavicons",
};
class bw_EnableFaviconMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_42_move_enable_favicon_to_domain_settings_state_provider_awaiter(this, void 0, void 0, function* () {
            // global state ("disableFavicon" -> "showFavicons")
            const globalState = yield helper.get("global");
            if ((globalState === null || globalState === void 0 ? void 0 : globalState.disableFavicon) != null) {
                yield helper.setToGlobal(bw_ShowFaviconDefinition, !globalState.disableFavicon);
                // delete `disableFavicon` from state global
                delete globalState.disableFavicon;
                yield helper.set("global", globalState);
            }
        });
    }
    rollback(helper) {
        return bw_42_move_enable_favicon_to_domain_settings_state_provider_awaiter(this, void 0, void 0, function* () {
            // global state ("showFavicons" -> "disableFavicon")
            const globalState = (yield helper.get("global")) || {};
            const showFavicons = yield helper.getFromGlobal(bw_ShowFaviconDefinition);
            if (showFavicons != null) {
                yield helper.set("global", Object.assign(Object.assign({}, globalState), { disableFavicon: !showFavicons }));
                // remove the global state provider framework key for `showFavicons`
                yield helper.setToGlobal(bw_ShowFaviconDefinition, null);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/43-move-auto-confirm-finger-prints-to-state-provider.ts
var bw_43_move_auto_confirm_finger_prints_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_ORGANIZATION_MANAGEMENT_PREFERENCES = {
    name: "organizationManagementPreferences",
};
const bw_AUTO_CONFIRM_FINGERPRINTS = {
    key: "autoConfirmFingerPrints",
    stateDefinition: bw_ORGANIZATION_MANAGEMENT_PREFERENCES,
};
class bw_AutoConfirmFingerPrintsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_43_move_auto_confirm_finger_prints_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            yield Promise.all(legacyAccounts.map((_a) => bw_43_move_auto_confirm_finger_prints_to_state_provider_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c;
                if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.autoConfirmFingerPrints) != null) {
                    yield helper.setToUser(userId, bw_AUTO_CONFIRM_FINGERPRINTS, account.settings.autoConfirmFingerPrints);
                    (_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? true : delete _c.autoConfirmFingerPrints;
                    yield helper.set(userId, account);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_43_move_auto_confirm_finger_prints_to_state_provider_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId, account) {
                return bw_43_move_auto_confirm_finger_prints_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    let updatedAccount = false;
                    const autoConfirmFingerPrints = yield helper.getFromUser(userId, bw_AUTO_CONFIRM_FINGERPRINTS);
                    if (autoConfirmFingerPrints) {
                        if (!account) {
                            account = {};
                        }
                        updatedAccount = true;
                        account.settings.autoConfirmFingerPrints = autoConfirmFingerPrints;
                        yield helper.setToUser(userId, bw_AUTO_CONFIRM_FINGERPRINTS, null);
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackUser(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/44-move-user-decryption-options-to-state-provider.ts
var bw_44_move_user_decryption_options_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_44_move_user_decryption_options_to_state_provider_USER_DECRYPTION_OPTIONS = {
    key: "decryptionOptions",
    stateDefinition: {
        name: "userDecryptionOptions",
    },
};
class bw_UserDecryptionOptionsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_44_move_user_decryption_options_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_44_move_user_decryption_options_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    const value = account === null || account === void 0 ? void 0 : account.decryptionOptions;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_44_move_user_decryption_options_to_state_provider_USER_DECRYPTION_OPTIONS, value);
                        delete account.decryptionOptions;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_44_move_user_decryption_options_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_44_move_user_decryption_options_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    const value = yield helper.getFromUser(userId, bw_44_move_user_decryption_options_to_state_provider_USER_DECRYPTION_OPTIONS);
                    if (account) {
                        account.decryptionOptions = Object.assign(account.decryptionOptions, value);
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_44_move_user_decryption_options_to_state_provider_USER_DECRYPTION_OPTIONS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/45-merge-environment-state.ts
var bw_45_merge_environment_state_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_45_merge_environment_state_ENVIRONMENT_STATE = { name: "environment" };
const bw_ENVIRONMENT_REGION = {
    key: "region",
    stateDefinition: bw_45_merge_environment_state_ENVIRONMENT_STATE,
};
const bw_ENVIRONMENT_URLS = {
    key: "urls",
    stateDefinition: bw_45_merge_environment_state_ENVIRONMENT_STATE,
};
const bw_ENVIRONMENT_ENVIRONMENT = {
    key: "environment",
    stateDefinition: bw_45_merge_environment_state_ENVIRONMENT_STATE,
};
class bw_MergeEnvironmentState extends bw_Migrator {
    migrate(helper) {
        return bw_45_merge_environment_state_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_45_merge_environment_state_awaiter(this, void 0, void 0, function* () {
                    const region = yield helper.getFromUser(userId, bw_ENVIRONMENT_REGION);
                    const urls = yield helper.getFromUser(userId, bw_ENVIRONMENT_URLS);
                    if (region == null && urls == null) {
                        return;
                    }
                    yield helper.setToUser(userId, bw_ENVIRONMENT_ENVIRONMENT, {
                        region,
                        urls,
                    });
                    yield helper.removeFromUser(userId, bw_ENVIRONMENT_REGION);
                    yield helper.removeFromUser(userId, bw_ENVIRONMENT_URLS);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            const region = yield helper.getFromGlobal(bw_ENVIRONMENT_REGION);
            const urls = yield helper.getFromGlobal(bw_ENVIRONMENT_URLS);
            if (region == null && urls == null) {
                return;
            }
            yield helper.setToGlobal(bw_ENVIRONMENT_ENVIRONMENT, {
                region,
                urls,
            });
            yield helper.removeFromGlobal(bw_ENVIRONMENT_REGION);
            yield helper.removeFromGlobal(bw_ENVIRONMENT_URLS);
        });
    }
    rollback(helper) {
        return bw_45_merge_environment_state_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_45_merge_environment_state_awaiter(this, void 0, void 0, function* () {
                    const state = (yield helper.getFromUser(userId, bw_ENVIRONMENT_ENVIRONMENT));
                    yield helper.setToUser(userId, bw_ENVIRONMENT_REGION, state === null || state === void 0 ? void 0 : state.region);
                    yield helper.setToUser(userId, bw_ENVIRONMENT_URLS, state === null || state === void 0 ? void 0 : state.urls);
                    yield helper.removeFromUser(userId, bw_ENVIRONMENT_ENVIRONMENT);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
            const state = (yield helper.getFromGlobal(bw_ENVIRONMENT_ENVIRONMENT));
            yield helper.setToGlobal(bw_ENVIRONMENT_REGION, state === null || state === void 0 ? void 0 : state.region);
            yield helper.setToGlobal(bw_ENVIRONMENT_URLS, state === null || state === void 0 ? void 0 : state.urls);
            yield helper.removeFromGlobal(bw_ENVIRONMENT_ENVIRONMENT);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/46-delete-orphaned-biometric-prompt-data.ts
var bw_46_delete_orphaned_biometric_prompt_data_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_46_delete_orphaned_biometric_prompt_data_PROMPT_CANCELLED = {
    key: "promptCancelled",
    stateDefinition: { name: "biometricSettings" },
};
class bw_DeleteBiometricPromptCancelledData extends bw_Migrator {
    migrate(helper) {
        return bw_46_delete_orphaned_biometric_prompt_data_awaiter(this, void 0, void 0, function* () {
            yield Promise.all((yield helper.getAccounts()).map((_a) => bw_46_delete_orphaned_biometric_prompt_data_awaiter(this, [_a], void 0, function* ({ userId }) {
                if (helper.getFromUser(userId, bw_46_delete_orphaned_biometric_prompt_data_PROMPT_CANCELLED) != null) {
                    yield helper.removeFromUser(userId, bw_46_delete_orphaned_biometric_prompt_data_PROMPT_CANCELLED);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_46_delete_orphaned_biometric_prompt_data_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/47-move-desktop-settings.ts
var bw_47_move_desktop_settings_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_DESKTOP_SETTINGS_STATE = { name: "desktopSettings" };
const bw_WINDOW_KEY = { key: "window", stateDefinition: bw_DESKTOP_SETTINGS_STATE };
const bw_CLOSE_TO_TRAY_KEY = {
    key: "closeToTray",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
const bw_MINIMIZE_TO_TRAY_KEY = {
    key: "minimizeToTray",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
const bw_START_TO_TRAY_KEY = {
    key: "startToTray",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
const bw_TRAY_ENABLED_KEY = {
    key: "trayEnabled",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
const bw_OPEN_AT_LOGIN_KEY = {
    key: "openAtLogin",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
const bw_ALWAYS_SHOW_DOCK_KEY = {
    key: "alwaysShowDock",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
const bw_ALWAYS_ON_TOP_KEY = {
    key: "alwaysOnTop",
    stateDefinition: bw_DESKTOP_SETTINGS_STATE,
};
class bw_MoveDesktopSettingsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_47_move_desktop_settings_awaiter(this, void 0, void 0, function* () {
            const legacyGlobal = yield helper.get("global");
            let updatedGlobal = false;
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.window) !== undefined) {
                yield helper.setToGlobal(bw_WINDOW_KEY, legacyGlobal.window);
                updatedGlobal = true;
                delete legacyGlobal.window;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableCloseToTray) != null) {
                yield helper.setToGlobal(bw_CLOSE_TO_TRAY_KEY, legacyGlobal.enableCloseToTray);
                updatedGlobal = true;
                delete legacyGlobal.enableCloseToTray;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableMinimizeToTray) != null) {
                yield helper.setToGlobal(bw_MINIMIZE_TO_TRAY_KEY, legacyGlobal.enableMinimizeToTray);
                updatedGlobal = true;
                delete legacyGlobal.enableMinimizeToTray;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableStartToTray) != null) {
                yield helper.setToGlobal(bw_START_TO_TRAY_KEY, legacyGlobal.enableStartToTray);
                updatedGlobal = true;
                delete legacyGlobal.enableStartToTray;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableTray) != null) {
                yield helper.setToGlobal(bw_TRAY_ENABLED_KEY, legacyGlobal.enableTray);
                updatedGlobal = true;
                delete legacyGlobal.enableTray;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.openAtLogin) != null) {
                yield helper.setToGlobal(bw_OPEN_AT_LOGIN_KEY, legacyGlobal.openAtLogin);
                updatedGlobal = true;
                delete legacyGlobal.openAtLogin;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.alwaysShowDock) != null) {
                yield helper.setToGlobal(bw_ALWAYS_SHOW_DOCK_KEY, legacyGlobal.alwaysShowDock);
                updatedGlobal = true;
                delete legacyGlobal.alwaysShowDock;
            }
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableAlwaysOnTop) != null) {
                yield helper.setToGlobal(bw_ALWAYS_ON_TOP_KEY, legacyGlobal.enableAlwaysOnTop);
                updatedGlobal = true;
                delete legacyGlobal.enableAlwaysOnTop;
            }
            if (updatedGlobal) {
                yield helper.set("global", legacyGlobal);
            }
            function migrateAccount(userId, account) {
                return bw_47_move_desktop_settings_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    // We only migrate the global setting for this, if we find it on the account object
                    // just delete it.
                    if (((_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.enableAlwaysOnTop) != null) {
                        delete account.settings.enableAlwaysOnTop;
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => migrateAccount(userId, account)));
        });
    }
    rollback(helper) {
        throw bw_IRREVERSIBLE;
    }
}

;// ../../libs/common/src/state-migrations/migrations/48-move-ddg-to-state-provider.ts
var bw_48_move_ddg_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_DDG_KEY = {
    key: "enableDuckDuckGoBrowserIntegration",
    stateDefinition: {
        name: "autofillSettings",
    },
};
class bw_MoveDdgToStateProviderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_48_move_ddg_to_state_provider_awaiter(this, void 0, void 0, function* () {
            // global state
            const global = yield helper.get("global");
            if ((global === null || global === void 0 ? void 0 : global.enableDuckDuckGoBrowserIntegration) == null) {
                return;
            }
            yield helper.setToGlobal(bw_DDG_KEY, global.enableDuckDuckGoBrowserIntegration);
            delete global.enableDuckDuckGoBrowserIntegration;
            yield helper.set("global", global);
        });
    }
    rollback(helper) {
        return bw_48_move_ddg_to_state_provider_awaiter(this, void 0, void 0, function* () {
            var _a;
            const enableDdg = yield helper.getFromGlobal(bw_DDG_KEY);
            if (!enableDdg) {
                return;
            }
            const global = (_a = (yield helper.get("global"))) !== null && _a !== void 0 ? _a : {};
            global.enableDuckDuckGoBrowserIntegration = enableDdg;
            yield helper.set("global", global);
            yield helper.removeFromGlobal(bw_DDG_KEY);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/49-move-account-server-configs.ts
var bw_49_move_account_server_configs_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_49_move_account_server_configs_CONFIG_DISK = { name: "config" };
const bw_49_move_account_server_configs_USER_SERVER_CONFIG = {
    stateDefinition: bw_49_move_account_server_configs_CONFIG_DISK,
    key: "serverConfig",
};
class bw_AccountServerConfigMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_49_move_account_server_configs_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_49_move_account_server_configs_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    if (((_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.serverConfig) != null) {
                        yield helper.setToUser(userId, bw_49_move_account_server_configs_USER_SERVER_CONFIG, account.settings.serverConfig);
                        delete account.settings.serverConfig;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_49_move_account_server_configs_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_49_move_account_server_configs_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const serverConfig = yield helper.getFromUser(userId, bw_49_move_account_server_configs_USER_SERVER_CONFIG);
                    if (serverConfig) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.settings) !== null && _a !== void 0 ? _a : (account.settings = {});
                        account.settings.serverConfig = serverConfig;
                        yield helper.setToUser(userId, bw_49_move_account_server_configs_USER_SERVER_CONFIG, null);
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/5-add-key-type-to-org-keys.ts
var bw_5_add_key_type_to_org_keys_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_AddKeyTypeToOrgKeysMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_5_add_key_type_to_org_keys_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function updateOrgKey(userId, account) {
                return bw_5_add_key_type_to_org_keys_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const encryptedOrgKeys = (_b = (_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.organizationKeys) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (encryptedOrgKeys == null) {
                        return;
                    }
                    const newOrgKeys = {};
                    Object.entries(encryptedOrgKeys).forEach(([orgId, encKey]) => {
                        newOrgKeys[orgId] = {
                            type: "organization",
                            key: encKey,
                        };
                    });
                    account.keys.organizationKeys.encrypted = newOrgKeys;
                    yield helper.set(userId, account);
                });
            }
            // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
            // eslint-disable-next-line @typescript-eslint/no-floating-promises
            Promise.all(accounts.map(({ userId, account }) => updateOrgKey(userId, account)));
        });
    }
    rollback(helper) {
        return bw_5_add_key_type_to_org_keys_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function updateOrgKey(userId, account) {
                return bw_5_add_key_type_to_org_keys_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const encryptedOrgKeys = (_b = (_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.organizationKeys) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (encryptedOrgKeys == null) {
                        return;
                    }
                    const newOrgKeys = {};
                    Object.entries(encryptedOrgKeys).forEach(([orgId, encKey]) => {
                        newOrgKeys[orgId] = encKey.key;
                    });
                    account.keys.organizationKeys.encrypted = newOrgKeys;
                    yield helper.set(userId, account);
                });
            }
            // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
            // eslint-disable-next-line @typescript-eslint/no-floating-promises
            Promise.all(accounts.map((_a) => bw_5_add_key_type_to_org_keys_awaiter(this, [_a], void 0, function* ({ userId, account }) { return updateOrgKey(userId, account); })));
        });
    }
    // Override is necessary because default implementation assumes `stateVersion` at the root, but for this version
    // it is nested inside a global object.
    updateVersion(helper, direction) {
        return bw_5_add_key_type_to_org_keys_awaiter(this, void 0, void 0, function* () {
            const endVersion = direction === "up" ? this.toVersion : this.fromVersion;
            helper.currentVersion = endVersion;
            const global = (yield helper.get("global")) || {};
            yield helper.set("global", Object.assign(Object.assign({}, global), { stateVersion: endVersion }));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/50-move-key-connector-to-state-provider.ts
var bw_50_move_key_connector_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_usesKeyConnectorKeyDefinition = {
    key: "usesKeyConnector",
    stateDefinition: {
        name: "keyConnector",
    },
};
const bw_convertAccountToKeyConnectorKeyDefinition = {
    key: "convertAccountToKeyConnector",
    stateDefinition: {
        name: "keyConnector",
    },
};
class bw_KeyConnectorMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_50_move_key_connector_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_50_move_key_connector_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const usesKeyConnector = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.usesKeyConnector;
                    const convertAccountToKeyConnector = (_b = account === null || account === void 0 ? void 0 : account.profile) === null || _b === void 0 ? void 0 : _b.convertAccountToKeyConnector;
                    if (usesKeyConnector == null && convertAccountToKeyConnector == null) {
                        return;
                    }
                    if (usesKeyConnector != null) {
                        yield helper.setToUser(userId, bw_usesKeyConnectorKeyDefinition, usesKeyConnector);
                        delete account.profile.usesKeyConnector;
                    }
                    if (convertAccountToKeyConnector != null) {
                        yield helper.setToUser(userId, bw_convertAccountToKeyConnectorKeyDefinition, convertAccountToKeyConnector);
                        delete account.profile.convertAccountToKeyConnector;
                    }
                    yield helper.set(userId, account);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_50_move_key_connector_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_50_move_key_connector_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    const usesKeyConnector = yield helper.getFromUser(userId, bw_usesKeyConnectorKeyDefinition);
                    const convertAccountToKeyConnector = yield helper.getFromUser(userId, bw_convertAccountToKeyConnectorKeyDefinition);
                    if (usesKeyConnector == null && convertAccountToKeyConnector == null) {
                        return;
                    }
                    if (usesKeyConnector != null) {
                        account.profile.usesKeyConnector = usesKeyConnector;
                        yield helper.setToUser(userId, bw_usesKeyConnectorKeyDefinition, null);
                    }
                    if (convertAccountToKeyConnector != null) {
                        account.profile.convertAccountToKeyConnector = convertAccountToKeyConnector;
                        yield helper.setToUser(userId, bw_convertAccountToKeyConnectorKeyDefinition, null);
                    }
                    yield helper.set(userId, account);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/51-move-remembered-email-to-state-providers.ts
var bw_51_move_remembered_email_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_LOGIN_EMAIL_STATE = { name: "loginEmail" };
const bw_51_move_remembered_email_to_state_providers_STORED_EMAIL = {
    key: "storedEmail",
    stateDefinition: bw_LOGIN_EMAIL_STATE,
};
class bw_RememberedEmailMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_51_move_remembered_email_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const legacyGlobal = yield helper.get("global");
            // Move global data
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.rememberedEmail) != null) {
                yield helper.setToGlobal(bw_51_move_remembered_email_to_state_providers_STORED_EMAIL, legacyGlobal.rememberedEmail);
            }
            // Delete legacy global data
            legacyGlobal === null || legacyGlobal === void 0 ? true : delete legacyGlobal.rememberedEmail;
            yield helper.set("global", legacyGlobal);
        });
    }
    rollback(helper) {
        return bw_51_move_remembered_email_to_state_providers_awaiter(this, void 0, void 0, function* () {
            let legacyGlobal = yield helper.get("global");
            let updatedLegacyGlobal = false;
            const globalStoredEmail = yield helper.getFromGlobal(bw_51_move_remembered_email_to_state_providers_STORED_EMAIL);
            if (globalStoredEmail) {
                if (!legacyGlobal) {
                    legacyGlobal = {};
                }
                updatedLegacyGlobal = true;
                legacyGlobal.rememberedEmail = globalStoredEmail;
                yield helper.setToGlobal(bw_51_move_remembered_email_to_state_providers_STORED_EMAIL, null);
            }
            if (updatedLegacyGlobal) {
                yield helper.set("global", legacyGlobal);
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/52-delete-installed-version.ts
var bw_52_delete_installed_version_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_DeleteInstalledVersion extends bw_Migrator {
    migrate(helper) {
        return bw_52_delete_installed_version_awaiter(this, void 0, void 0, function* () {
            const legacyGlobal = yield helper.get("global");
            if ((legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.installedVersion) != null) {
                delete legacyGlobal.installedVersion;
                yield helper.set("global", legacyGlobal);
            }
        });
    }
    rollback(helper) {
        throw bw_IRREVERSIBLE;
    }
}

;// ../../libs/common/src/state-migrations/migrations/53-migrate-device-trust-svc-to-state-providers.ts
var bw_53_migrate_device_trust_svc_to_state_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_53_migrate_device_trust_svc_to_state_providers_DEVICE_KEY = {
    key: "deviceKey", // matches KeyDefinition.key in DeviceTrustService
    stateDefinition: {
        name: "deviceTrust", // matches StateDefinition.name in StateDefinitions
    },
};
const bw_53_migrate_device_trust_svc_to_state_providers_SHOULD_TRUST_DEVICE = {
    key: "shouldTrustDevice",
    stateDefinition: {
        name: "deviceTrust",
    },
};
class bw_DeviceTrustServiceStateProviderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_53_migrate_device_trust_svc_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_53_migrate_device_trust_svc_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    let updatedAccount = false;
                    // Migrate deviceKey
                    const existingDeviceKey = (_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.deviceKey;
                    if (existingDeviceKey != null) {
                        // Only migrate data that exists
                        yield helper.setToUser(userId, bw_53_migrate_device_trust_svc_to_state_providers_DEVICE_KEY, existingDeviceKey);
                        delete account.keys.deviceKey;
                        updatedAccount = true;
                    }
                    // Migrate shouldTrustDevice
                    const existingShouldTrustDevice = (_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.trustDeviceChoiceForDecryption;
                    if (existingShouldTrustDevice != null) {
                        yield helper.setToUser(userId, bw_53_migrate_device_trust_svc_to_state_providers_SHOULD_TRUST_DEVICE, existingShouldTrustDevice);
                        delete account.settings.trustDeviceChoiceForDecryption;
                        updatedAccount = true;
                    }
                    if (updatedAccount) {
                        // Save the migrated account
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_53_migrate_device_trust_svc_to_state_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_53_migrate_device_trust_svc_to_state_providers_awaiter(this, void 0, void 0, function* () {
                    // Rollback deviceKey
                    const migratedDeviceKey = yield helper.getFromUser(userId, bw_53_migrate_device_trust_svc_to_state_providers_DEVICE_KEY);
                    if ((account === null || account === void 0 ? void 0 : account.keys) && migratedDeviceKey != null) {
                        account.keys.deviceKey = migratedDeviceKey;
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_53_migrate_device_trust_svc_to_state_providers_DEVICE_KEY, null);
                    // Rollback shouldTrustDevice
                    const migratedShouldTrustDevice = yield helper.getFromUser(userId, bw_53_migrate_device_trust_svc_to_state_providers_SHOULD_TRUST_DEVICE);
                    if ((account === null || account === void 0 ? void 0 : account.settings) && migratedShouldTrustDevice != null) {
                        account.settings.trustDeviceChoiceForDecryption = migratedShouldTrustDevice;
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_53_migrate_device_trust_svc_to_state_providers_SHOULD_TRUST_DEVICE, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/54-move-encrypted-sends.ts
var bw_54_move_encrypted_sends_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

var bw_54_move_encrypted_sends_SendType;
(function (SendType) {
    SendType[SendType["Text"] = 0] = "Text";
    SendType[SendType["File"] = 1] = "File";
})(bw_54_move_encrypted_sends_SendType || (bw_54_move_encrypted_sends_SendType = {}));
const bw_ENCRYPTED_SENDS = {
    stateDefinition: {
        name: "send",
    },
    key: "sends",
};
/**
 * Only encrypted sends are stored on disk. Only the encrypted items need to be
 * migrated from the previous sends state data.
 */
class bw_SendMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_54_move_encrypted_sends_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_54_move_encrypted_sends_awaiter(this, void 0, void 0, function* () {
                    var _a, _b;
                    const value = (_b = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.sends) === null || _b === void 0 ? void 0 : _b.encrypted;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_ENCRYPTED_SENDS, value);
                        delete account.data.sends;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_54_move_encrypted_sends_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_54_move_encrypted_sends_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_ENCRYPTED_SENDS);
                    if (account) {
                        account.data = Object.assign((_a = account.data) !== null && _a !== void 0 ? _a : {}, {
                            sends: {
                                encrypted: value,
                            },
                        });
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_ENCRYPTED_SENDS, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/55-move-master-key-state-to-provider.ts
var bw_55_move_master_key_state_to_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_FORCE_SET_PASSWORD_REASON_DEFINITION = {
    key: "forceSetPasswordReason",
    stateDefinition: {
        name: "masterPassword",
    },
};
const bw_MASTER_KEY_HASH_DEFINITION = {
    key: "masterKeyHash",
    stateDefinition: {
        name: "masterPassword",
    },
};
const bw_MASTER_KEY_ENCRYPTED_USER_KEY_DEFINITION = {
    key: "masterKeyEncryptedUserKey",
    stateDefinition: {
        name: "masterPassword",
    },
};
class bw_MoveMasterKeyStateToProviderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_55_move_master_key_state_to_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_55_move_master_key_state_to_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c;
                    const forceSetPasswordReason = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.forceSetPasswordReason;
                    if (forceSetPasswordReason != null) {
                        yield helper.setToUser(userId, bw_FORCE_SET_PASSWORD_REASON_DEFINITION, forceSetPasswordReason);
                        delete account.profile.forceSetPasswordReason;
                        yield helper.set(userId, account);
                    }
                    const masterKeyHash = (_b = account === null || account === void 0 ? void 0 : account.profile) === null || _b === void 0 ? void 0 : _b.keyHash;
                    if (masterKeyHash != null) {
                        yield helper.setToUser(userId, bw_MASTER_KEY_HASH_DEFINITION, masterKeyHash);
                        delete account.profile.keyHash;
                        yield helper.set(userId, account);
                    }
                    const masterKeyEncryptedUserKey = (_c = account === null || account === void 0 ? void 0 : account.keys) === null || _c === void 0 ? void 0 : _c.masterKeyEncryptedUserKey;
                    if (masterKeyEncryptedUserKey != null) {
                        yield helper.setToUser(userId, bw_MASTER_KEY_ENCRYPTED_USER_KEY_DEFINITION, masterKeyEncryptedUserKey);
                        delete account.keys.masterKeyEncryptedUserKey;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_55_move_master_key_state_to_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_55_move_master_key_state_to_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c;
                    const forceSetPasswordReason = yield helper.getFromUser(userId, bw_FORCE_SET_PASSWORD_REASON_DEFINITION);
                    const masterKeyHash = yield helper.getFromUser(userId, bw_MASTER_KEY_HASH_DEFINITION);
                    const masterKeyEncryptedUserKey = yield helper.getFromUser(userId, bw_MASTER_KEY_ENCRYPTED_USER_KEY_DEFINITION);
                    if (account != null) {
                        if (forceSetPasswordReason != null) {
                            account.profile = Object.assign((_a = account.profile) !== null && _a !== void 0 ? _a : {}, {
                                forceSetPasswordReason,
                            });
                        }
                        if (masterKeyHash != null) {
                            account.profile = Object.assign((_b = account.profile) !== null && _b !== void 0 ? _b : {}, {
                                keyHash: masterKeyHash,
                            });
                        }
                        if (masterKeyEncryptedUserKey != null) {
                            account.keys = Object.assign((_c = account.keys) !== null && _c !== void 0 ? _c : {}, {
                                masterKeyEncryptedUserKey,
                            });
                        }
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_FORCE_SET_PASSWORD_REASON_DEFINITION, null);
                    yield helper.setToUser(userId, bw_MASTER_KEY_HASH_DEFINITION, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/56-move-auth-requests.ts
var bw_56_move_auth_requests_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_56_move_auth_requests_ADMIN_AUTH_REQUEST_KEY = {
    stateDefinition: {
        name: "authRequestLocal",
    },
    key: "adminAuthRequest",
};
const bw_ACCEPT_AUTH_REQUESTS_KEY = {
    stateDefinition: {
        name: "authRequestLocal",
    },
    key: "acceptAuthRequests",
};
class bw_AuthRequestMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_56_move_auth_requests_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_56_move_auth_requests_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    let updatedAccount = false;
                    // Migrate admin auth request
                    const existingAdminAuthRequest = account === null || account === void 0 ? void 0 : account.adminAuthRequest;
                    if (existingAdminAuthRequest != null) {
                        yield helper.setToUser(userId, bw_56_move_auth_requests_ADMIN_AUTH_REQUEST_KEY, existingAdminAuthRequest);
                        delete account.adminAuthRequest;
                        updatedAccount = true;
                    }
                    // Migrate approve login requests
                    const existingApproveLoginRequests = (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.approveLoginRequests;
                    if (existingApproveLoginRequests != null) {
                        yield helper.setToUser(userId, bw_ACCEPT_AUTH_REQUESTS_KEY, existingApproveLoginRequests);
                        delete account.settings.approveLoginRequests;
                        updatedAccount = true;
                    }
                    if (updatedAccount) {
                        // Save the migrated account
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_56_move_auth_requests_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_56_move_auth_requests_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    let updatedAccount = false;
                    // Rollback admin auth request
                    const migratedAdminAuthRequest = yield helper.getFromUser(userId, bw_56_move_auth_requests_ADMIN_AUTH_REQUEST_KEY);
                    if (migratedAdminAuthRequest != null) {
                        account.adminAuthRequest = migratedAdminAuthRequest;
                        updatedAccount = true;
                    }
                    yield helper.setToUser(userId, bw_56_move_auth_requests_ADMIN_AUTH_REQUEST_KEY, null);
                    // Rollback approve login requests
                    const migratedAcceptAuthRequest = yield helper.getFromUser(userId, bw_ACCEPT_AUTH_REQUESTS_KEY);
                    if (migratedAcceptAuthRequest != null) {
                        account.settings = Object.assign((_a = account.settings) !== null && _a !== void 0 ? _a : {}, {
                            approveLoginRequests: migratedAcceptAuthRequest,
                        });
                        updatedAccount = true;
                    }
                    yield helper.setToUser(userId, bw_ACCEPT_AUTH_REQUESTS_KEY, null);
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/57-move-cipher-service-to-state-provider.ts
var bw_57_move_cipher_service_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK_LOCAL = {
    key: "localData",
    stateDefinition: {
        name: "ciphersLocal",
    },
};
const bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK = {
    key: "ciphers",
    stateDefinition: {
        name: "ciphers",
    },
};
class bw_CipherServiceMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_57_move_cipher_service_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_57_move_cipher_service_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c;
                    let updatedAccount = false;
                    //Migrate localData
                    const localData = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.localData;
                    if (localData != null) {
                        yield helper.setToUser(userId, bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK_LOCAL, localData);
                        delete account.data.localData;
                        updatedAccount = true;
                    }
                    //Migrate ciphers
                    const ciphers = (_c = (_b = account === null || account === void 0 ? void 0 : account.data) === null || _b === void 0 ? void 0 : _b.ciphers) === null || _c === void 0 ? void 0 : _c.encrypted;
                    if (ciphers != null) {
                        yield helper.setToUser(userId, bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK, ciphers);
                        delete account.data.ciphers;
                        updatedAccount = true;
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_57_move_cipher_service_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_57_move_cipher_service_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    //rollback localData
                    const localData = yield helper.getFromUser(userId, bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK_LOCAL);
                    if (account.data && localData != null) {
                        account.data.localData = localData;
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK_LOCAL, null);
                    //rollback ciphers
                    const ciphers = yield helper.getFromUser(userId, bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK);
                    if (account.data && ciphers != null) {
                        (_a = account.data).ciphers || (_a.ciphers = { encrypted: null });
                        account.data.ciphers.encrypted = ciphers;
                        yield helper.set(userId, account);
                    }
                    yield helper.setToUser(userId, bw_57_move_cipher_service_to_state_provider_CIPHERS_DISK, null);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/58-remove-refresh-token-migrated-state-provider-flag.ts
var bw_58_remove_refresh_token_migrated_state_provider_flag_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_REFRESH_TOKEN_MIGRATED_TO_SECURE_STORAGE = {
    key: "refreshTokenMigratedToSecureStorage", // matches KeyDefinition.key
    stateDefinition: {
        name: "token", // matches StateDefinition.name in StateDefinitions
    },
};
class bw_RemoveRefreshTokenMigratedFlagMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_58_remove_refresh_token_migrated_state_provider_flag_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_58_remove_refresh_token_migrated_state_provider_flag_awaiter(this, void 0, void 0, function* () {
                    const refreshTokenMigratedFlag = yield helper.getFromUser(userId, bw_REFRESH_TOKEN_MIGRATED_TO_SECURE_STORAGE);
                    if (refreshTokenMigratedFlag != null) {
                        // Only delete the flag if it exists
                        yield helper.removeFromUser(userId, bw_REFRESH_TOKEN_MIGRATED_TO_SECURE_STORAGE);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_58_remove_refresh_token_migrated_state_provider_flag_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/59-move-kdf-config-to-state-provider.ts
var bw_59_move_kdf_config_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

var bw_59_move_kdf_config_to_state_provider_KdfType;
(function (KdfType) {
    KdfType[KdfType["PBKDF2_SHA256"] = 0] = "PBKDF2_SHA256";
    KdfType[KdfType["Argon2id"] = 1] = "Argon2id";
})(bw_59_move_kdf_config_to_state_provider_KdfType || (bw_59_move_kdf_config_to_state_provider_KdfType = {}));
class bw_KdfConfig {
}
const bw_kdfConfigKeyDefinition = {
    key: "kdfConfig",
    stateDefinition: {
        name: "kdfConfig",
    },
};
class bw_KdfConfigMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_59_move_kdf_config_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_59_move_kdf_config_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c, _d, _e, _f, _g, _h;
                    const iterations = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.kdfIterations;
                    const kdfType = (_b = account === null || account === void 0 ? void 0 : account.profile) === null || _b === void 0 ? void 0 : _b.kdfType;
                    const memory = (_c = account === null || account === void 0 ? void 0 : account.profile) === null || _c === void 0 ? void 0 : _c.kdfMemory;
                    const parallelism = (_d = account === null || account === void 0 ? void 0 : account.profile) === null || _d === void 0 ? void 0 : _d.kdfParallelism;
                    const kdfConfig = {
                        iterations: iterations,
                        kdfType: kdfType,
                        memory: memory,
                        parallelism: parallelism,
                    };
                    if (kdfConfig != null) {
                        yield helper.setToUser(userId, bw_kdfConfigKeyDefinition, kdfConfig);
                        (_e = account === null || account === void 0 ? void 0 : account.profile) === null || _e === void 0 ? true : delete _e.kdfIterations;
                        (_f = account === null || account === void 0 ? void 0 : account.profile) === null || _f === void 0 ? true : delete _f.kdfType;
                        (_g = account === null || account === void 0 ? void 0 : account.profile) === null || _g === void 0 ? true : delete _g.kdfMemory;
                        (_h = account === null || account === void 0 ? void 0 : account.profile) === null || _h === void 0 ? true : delete _h.kdfParallelism;
                    }
                    yield helper.set(userId, account);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_59_move_kdf_config_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_59_move_kdf_config_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    const kdfConfig = yield helper.getFromUser(userId, bw_kdfConfigKeyDefinition);
                    if (kdfConfig != null) {
                        account.profile.kdfIterations = kdfConfig.iterations;
                        account.profile.kdfType = kdfConfig.kdfType;
                        account.profile.kdfMemory = kdfConfig.memory;
                        account.profile.kdfParallelism = kdfConfig.parallelism;
                        yield helper.setToUser(userId, bw_kdfConfigKeyDefinition, null);
                    }
                    yield helper.set(userId, account);
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/6-remove-legacy-etm-key.ts
var bw_6_remove_legacy_etm_key_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_RemoveLegacyEtmKeyMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_6_remove_legacy_etm_key_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function updateAccount(userId, account) {
                return bw_6_remove_legacy_etm_key_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    if ((_a = account === null || account === void 0 ? void 0 : account.keys) === null || _a === void 0 ? void 0 : _a.legacyEtmKey) {
                        delete account.keys.legacyEtmKey;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all(accounts.map(({ userId, account }) => updateAccount(userId, account)));
        });
    }
    rollback(helper) {
        return bw_6_remove_legacy_etm_key_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
    // Override is necessary because default implementation assumes `stateVersion` at the root, but for this version
    // it is nested inside a global object.
    updateVersion(helper, direction) {
        return bw_6_remove_legacy_etm_key_awaiter(this, void 0, void 0, function* () {
            const endVersion = direction === "up" ? this.toVersion : this.fromVersion;
            helper.currentVersion = endVersion;
            const global = (yield helper.get("global")) || {};
            yield helper.set("global", Object.assign(Object.assign({}, global), { stateVersion: endVersion }));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/60-known-accounts.ts
var bw_60_known_accounts_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_60_known_accounts_ACCOUNT_ACCOUNTS = {
    stateDefinition: {
        name: "account",
    },
    key: "accounts",
};
const bw_60_known_accounts_ACCOUNT_ACTIVE_ACCOUNT_ID = {
    stateDefinition: {
        name: "account",
    },
    key: "activeAccountId",
};
const bw_60_known_accounts_ACCOUNT_ACTIVITY = {
    stateDefinition: {
        name: "account",
    },
    key: "activity",
};
class bw_KnownAccountsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_60_known_accounts_awaiter(this, void 0, void 0, function* () {
            yield this.migrateAuthenticatedAccounts(helper);
            yield this.migrateActiveAccountId(helper);
            yield this.migrateAccountActivity(helper);
        });
    }
    rollback(helper) {
        return bw_60_known_accounts_awaiter(this, void 0, void 0, function* () {
            var _a;
            // authenticated account are removed, but the accounts record also contains logged out accounts. Best we can do is to add them all back
            const userIds = (_a = (yield helper.getKnownUserIds())) !== null && _a !== void 0 ? _a : [];
            yield helper.set("authenticatedAccounts", userIds);
            yield helper.removeFromGlobal(bw_60_known_accounts_ACCOUNT_ACCOUNTS);
            // Active Account Id
            const activeAccountId = yield helper.getFromGlobal(bw_60_known_accounts_ACCOUNT_ACTIVE_ACCOUNT_ID);
            if (activeAccountId) {
                yield helper.set("activeUserId", activeAccountId);
            }
            yield helper.removeFromGlobal(bw_60_known_accounts_ACCOUNT_ACTIVE_ACCOUNT_ID);
            // Account Activity
            const accountActivity = yield helper.getFromGlobal(bw_60_known_accounts_ACCOUNT_ACTIVITY);
            if (accountActivity) {
                const toStore = Object.entries(accountActivity).reduce((agg, [userId, dateString]) => {
                    agg[userId] = new Date(dateString).getTime();
                    return agg;
                }, {});
                yield helper.set("accountActivity", toStore);
            }
            yield helper.removeFromGlobal(bw_60_known_accounts_ACCOUNT_ACTIVITY);
        });
    }
    migrateAuthenticatedAccounts(helper) {
        return bw_60_known_accounts_awaiter(this, void 0, void 0, function* () {
            var _a;
            const authenticatedAccounts = (_a = (yield helper.get("authenticatedAccounts"))) !== null && _a !== void 0 ? _a : [];
            const accounts = yield Promise.all(authenticatedAccounts.map((userId) => bw_60_known_accounts_awaiter(this, void 0, void 0, function* () {
                const account = yield helper.get(userId);
                return { userId, account };
            })));
            const accountsToStore = accounts.reduce((agg, { userId, account }) => {
                var _a, _b;
                if (account === null || account === void 0 ? void 0 : account.profile) {
                    agg[userId] = {
                        email: (_a = account.profile.email) !== null && _a !== void 0 ? _a : "",
                        emailVerified: (_b = account.profile.emailVerified) !== null && _b !== void 0 ? _b : false,
                        name: account.profile.name,
                    };
                }
                return agg;
            }, {});
            yield helper.setToGlobal(bw_60_known_accounts_ACCOUNT_ACCOUNTS, accountsToStore);
            yield helper.remove("authenticatedAccounts");
        });
    }
    migrateAccountActivity(helper) {
        return bw_60_known_accounts_awaiter(this, void 0, void 0, function* () {
            const stored = yield helper.get("accountActivity");
            const accountActivity = Object.entries(stored !== null && stored !== void 0 ? stored : {}).reduce((agg, [userId, dateMs]) => {
                agg[userId] = JSON.stringify(new Date(dateMs));
                return agg;
            }, {});
            yield helper.setToGlobal(bw_60_known_accounts_ACCOUNT_ACTIVITY, accountActivity);
            yield helper.remove("accountActivity");
        });
    }
    migrateActiveAccountId(helper) {
        return bw_60_known_accounts_awaiter(this, void 0, void 0, function* () {
            const activeAccountId = yield helper.get("activeUserId");
            yield helper.setToGlobal(bw_60_known_accounts_ACCOUNT_ACTIVE_ACCOUNT_ID, activeAccountId);
            yield helper.remove("activeUserId");
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/61-move-pin-state-to-providers.ts
var bw_61_move_pin_state_to_providers_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_PIN_STATE = { name: "pinUnlock" };
const bw_61_move_pin_state_to_providers_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT = {
    stateDefinition: bw_PIN_STATE,
    key: "pinKeyEncryptedUserKeyPersistent",
};
const bw_61_move_pin_state_to_providers_USER_KEY_ENCRYPTED_PIN = {
    stateDefinition: bw_PIN_STATE,
    key: "userKeyEncryptedPin",
};
const bw_61_move_pin_state_to_providers_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY = {
    stateDefinition: bw_PIN_STATE,
    key: "oldPinKeyEncryptedMasterKey",
};
class bw_PinStateMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_61_move_pin_state_to_providers_awaiter(this, void 0, void 0, function* () {
            const legacyAccounts = yield helper.getAccounts();
            let updatedAccount = false;
            function migrateAccount(userId, account) {
                return bw_61_move_pin_state_to_providers_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c, _d;
                    // Migrate pinKeyEncryptedUserKey (to `pinKeyEncryptedUserKeyPersistent`)
                    if (((_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.pinKeyEncryptedUserKey) != null) {
                        yield helper.setToUser(userId, bw_61_move_pin_state_to_providers_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT, account.settings.pinKeyEncryptedUserKey);
                        delete account.settings.pinKeyEncryptedUserKey;
                        updatedAccount = true;
                    }
                    // Migrate protectedPin (to `userKeyEncryptedPin`)
                    if (((_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? void 0 : _b.protectedPin) != null) {
                        yield helper.setToUser(userId, bw_61_move_pin_state_to_providers_USER_KEY_ENCRYPTED_PIN, account.settings.protectedPin);
                        delete account.settings.protectedPin;
                        updatedAccount = true;
                    }
                    // Migrate pinProtected (to `oldPinKeyEncryptedMasterKey`)
                    if (((_d = (_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? void 0 : _c.pinProtected) === null || _d === void 0 ? void 0 : _d.encrypted) != null) {
                        yield helper.setToUser(userId, bw_61_move_pin_state_to_providers_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY, account.settings.pinProtected.encrypted);
                        delete account.settings.pinProtected;
                        updatedAccount = true;
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([
                ...legacyAccounts.map(({ userId, account }) => migrateAccount(userId, account)),
            ]);
        });
    }
    rollback(helper) {
        return bw_61_move_pin_state_to_providers_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_61_move_pin_state_to_providers_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    let updatedAccount = false;
                    const accountPinKeyEncryptedUserKeyPersistent = yield helper.getFromUser(userId, bw_61_move_pin_state_to_providers_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT);
                    const accountUserKeyEncryptedPin = yield helper.getFromUser(userId, bw_61_move_pin_state_to_providers_USER_KEY_ENCRYPTED_PIN);
                    const accountOldPinKeyEncryptedMasterKey = yield helper.getFromUser(userId, bw_61_move_pin_state_to_providers_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY);
                    if (!account) {
                        account = {};
                    }
                    if (accountPinKeyEncryptedUserKeyPersistent != null) {
                        account.settings.pinKeyEncryptedUserKey = accountPinKeyEncryptedUserKeyPersistent;
                        yield helper.setToUser(userId, bw_61_move_pin_state_to_providers_PIN_KEY_ENCRYPTED_USER_KEY_PERSISTENT, null);
                        updatedAccount = true;
                    }
                    if (accountUserKeyEncryptedPin != null) {
                        account.settings.protectedPin = accountUserKeyEncryptedPin;
                        yield helper.setToUser(userId, bw_61_move_pin_state_to_providers_USER_KEY_ENCRYPTED_PIN, null);
                        updatedAccount = true;
                    }
                    if (accountOldPinKeyEncryptedMasterKey != null) {
                        account.settings = Object.assign((_a = account.settings) !== null && _a !== void 0 ? _a : {}, {
                            pinProtected: {
                                encrypted: accountOldPinKeyEncryptedMasterKey,
                            },
                        });
                        yield helper.setToUser(userId, bw_61_move_pin_state_to_providers_OLD_PIN_KEY_ENCRYPTED_MASTER_KEY, null);
                        updatedAccount = true;
                    }
                    if (updatedAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all(accounts.map(({ userId, account }) => rollbackAccount(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/62-migrate-vault-timeout-settings-svc-to-state-provider.ts
var bw_62_migrate_vault_timeout_settings_svc_to_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_VAULT_TIMEOUT_SETTINGS_STATE_DEF_LIKE = {
    name: "vaultTimeoutSettings",
};
const bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT = {
    key: "vaultTimeout", // matches KeyDefinition.key
    stateDefinition: bw_VAULT_TIMEOUT_SETTINGS_STATE_DEF_LIKE,
};
const bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT_ACTION = {
    key: "vaultTimeoutAction", // matches KeyDefinition.key
    stateDefinition: bw_VAULT_TIMEOUT_SETTINGS_STATE_DEF_LIKE,
};
// Define mapping of old values to new values for migration purposes
const bw_vaultTimeoutTypeMigrateRecord = {
    null: "never",
    "-1": "onRestart",
    "-2": "onLocked",
    "-3": "onSleep",
    "-4": "onIdle",
};
// define mapping of new values to old values for rollback purposes
const bw_vaultTimeoutTypeRollbackRecord = {
    never: null,
    onRestart: -1,
    onLocked: -2,
    onSleep: -3,
    onIdle: -4,
};
var bw_62_migrate_vault_timeout_settings_svc_to_state_provider_ClientType;
(function (ClientType) {
    ClientType["Web"] = "web";
    ClientType["Browser"] = "browser";
    ClientType["Desktop"] = "desktop";
    ClientType["Cli"] = "cli";
})(bw_62_migrate_vault_timeout_settings_svc_to_state_provider_ClientType || (bw_62_migrate_vault_timeout_settings_svc_to_state_provider_ClientType = {}));
class bw_VaultTimeoutSettingsServiceStateProviderMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_62_migrate_vault_timeout_settings_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const globalData = yield helper.get("global");
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_62_migrate_vault_timeout_settings_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    var _a, _b, _c, _d;
                    let updatedAccount = false;
                    // Migrate vault timeout
                    let existingVaultTimeout = (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.vaultTimeout;
                    if (helper.clientType === bw_62_migrate_vault_timeout_settings_svc_to_state_provider_ClientType.Cli && existingVaultTimeout === undefined) {
                        // The CLI does not set a vault timeout by default so we need to set it to null
                        // so that the migration can migrate null to "never" as the CLI does not have a vault timeout.
                        existingVaultTimeout = null;
                    }
                    if (existingVaultTimeout !== undefined) {
                        // check undefined so that we allow null values (previously meant never timeout)
                        // Only migrate data that exists
                        if (existingVaultTimeout === null || existingVaultTimeout < 0) {
                            // Map null or negative values to new string values
                            const newVaultTimeout = bw_vaultTimeoutTypeMigrateRecord[existingVaultTimeout];
                            yield helper.setToUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT, newVaultTimeout);
                        }
                        else {
                            // Persist positive numbers as is
                            yield helper.setToUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT, existingVaultTimeout);
                        }
                        (_b = account === null || account === void 0 ? void 0 : account.settings) === null || _b === void 0 ? true : delete _b.vaultTimeout;
                        updatedAccount = true;
                    }
                    // Migrate vault timeout action
                    const existingVaultTimeoutAction = (_c = account === null || account === void 0 ? void 0 : account.settings) === null || _c === void 0 ? void 0 : _c.vaultTimeoutAction;
                    if (existingVaultTimeoutAction != null) {
                        // Only migrate data that exists
                        yield helper.setToUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT_ACTION, existingVaultTimeoutAction);
                        (_d = account === null || account === void 0 ? void 0 : account.settings) === null || _d === void 0 ? true : delete _d.vaultTimeoutAction;
                        updatedAccount = true;
                    }
                    // Note: we are explicitly not worrying about mapping over the global fallback vault timeout / action
                    // into the new state provider framework.  It was originally a fallback but hasn't been used for years
                    // so this migration will clean up the global properties fully.
                    if (updatedAccount) {
                        // Save the migrated account only if it was updated
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
            // Delete global data (works for browser extension and web; CLI doesn't have these as global settings).
            globalData === null || globalData === void 0 ? true : delete globalData.vaultTimeout;
            globalData === null || globalData === void 0 ? true : delete globalData.vaultTimeoutAction;
            yield helper.set("global", globalData);
            // Remove desktop only settings. These aren't found by the above global key removal b/c of
            // the different storage key format. This removal does not cause any issues on migrating for other clients.
            yield helper.remove("global\\.vaultTimeout");
            yield helper.remove("global\\.vaultTimeoutAction");
        });
    }
    rollback(helper) {
        return bw_62_migrate_vault_timeout_settings_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function rollbackAccount(userId, account) {
                return bw_62_migrate_vault_timeout_settings_svc_to_state_provider_awaiter(this, void 0, void 0, function* () {
                    let updatedLegacyAccount = false;
                    // Rollback vault timeout
                    const migratedVaultTimeout = yield helper.getFromUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT);
                    if ((account === null || account === void 0 ? void 0 : account.settings) && migratedVaultTimeout != null) {
                        if (typeof migratedVaultTimeout === "string") {
                            // Map new string values back to old values
                            account.settings.vaultTimeout = bw_vaultTimeoutTypeRollbackRecord[migratedVaultTimeout];
                        }
                        else {
                            // persist numbers as is
                            account.settings.vaultTimeout = migratedVaultTimeout;
                        }
                        updatedLegacyAccount = true;
                    }
                    yield helper.setToUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT, null);
                    // Rollback vault timeout action
                    const migratedVaultTimeoutAction = yield helper.getFromUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT_ACTION);
                    if ((account === null || account === void 0 ? void 0 : account.settings) && migratedVaultTimeoutAction != null) {
                        account.settings.vaultTimeoutAction = migratedVaultTimeoutAction;
                        updatedLegacyAccount = true;
                    }
                    yield helper.setToUser(userId, bw_62_migrate_vault_timeout_settings_svc_to_state_provider_VAULT_TIMEOUT_ACTION, null);
                    if (updatedLegacyAccount) {
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => rollbackAccount(userId, account))]);
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/63-migrate-password-settings.ts
var bw_63_migrate_password_settings_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_NAVIGATION = {
    stateDefinition: {
        name: "generator",
    },
    key: "generatorSettings",
};
const bw_63_migrate_password_settings_PASSWORD = {
    stateDefinition: {
        name: "generator",
    },
    key: "passwordGeneratorSettings",
};
const bw_63_migrate_password_settings_PASSPHRASE = {
    stateDefinition: {
        name: "generator",
    },
    key: "passphraseGeneratorSettings",
};
class bw_PasswordOptionsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_63_migrate_password_settings_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_63_migrate_password_settings_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const legacyOptions = (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.passwordGenerationOptions;
                    if (legacyOptions) {
                        const converted = bw_convertSettings(legacyOptions);
                        yield bw_storeSettings(helper, userId, converted);
                        yield bw_deleteSettings(helper, userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_63_migrate_password_settings_awaiter(this, void 0, void 0, function* () {
            // not supported
        });
    }
}
function bw_convertSettings(options) {
    const password = {
        length: options.length,
        ambiguous: options.ambiguous,
        uppercase: options.uppercase,
        minUppercase: options.minUppercase,
        lowercase: options.lowercase,
        minLowercase: options.minLowercase,
        number: options.number,
        minNumber: options.minNumber,
        special: options.special,
        minSpecial: options.minSpecial,
    };
    const generator = {
        type: options.type,
    };
    const passphrase = {
        numWords: options.numWords,
        wordSeparator: options.wordSeparator,
        capitalize: options.capitalize,
        includeNumber: options.includeNumber,
    };
    return { generator, password, passphrase };
}
function bw_storeSettings(helper, userId, converted) {
    return bw_63_migrate_password_settings_awaiter(this, void 0, void 0, function* () {
        var _a;
        const existing = (_a = (yield helper.getFromUser(userId, bw_NAVIGATION))) !== null && _a !== void 0 ? _a : {};
        const updated = Object.assign(existing, converted.generator);
        yield Promise.all([
            helper.setToUser(userId, bw_NAVIGATION, updated),
            helper.setToUser(userId, bw_63_migrate_password_settings_PASSPHRASE, converted.passphrase),
            helper.setToUser(userId, bw_63_migrate_password_settings_PASSWORD, converted.password),
        ]);
    });
}
function bw_deleteSettings(helper, userId, account) {
    return bw_63_migrate_password_settings_awaiter(this, void 0, void 0, function* () {
        var _a;
        (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? true : delete _a.passwordGenerationOptions;
        yield helper.set(userId, account);
    });
}

;// ../../libs/common/src/state-migrations/migrations/64-migrate-generator-history.ts
var bw_64_migrate_generator_history_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_HISTORY = {
    stateDefinition: {
        name: "generator",
    },
    key: "localGeneratorHistoryBuffer",
};
class bw_GeneratorHistoryMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_64_migrate_generator_history_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_64_migrate_generator_history_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const data = (_a = account === null || account === void 0 ? void 0 : account.data) === null || _a === void 0 ? void 0 : _a.passwordGenerationHistory;
                    if (data && data.encrypted) {
                        yield helper.setToUser(userId, bw_HISTORY, data.encrypted);
                        delete account.data.passwordGenerationHistory;
                        yield helper.set(userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_64_migrate_generator_history_awaiter(this, void 0, void 0, function* () {
            // not supported
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/65-migrate-forwarder-settings.ts
var bw_65_migrate_forwarder_settings_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_65_migrate_forwarder_settings_NAVIGATION = {
    stateDefinition: {
        name: "generator",
    },
    key: "generatorSettings",
};
const bw_65_migrate_forwarder_settings_CATCHALL = {
    stateDefinition: {
        name: "generator",
    },
    key: "catchallGeneratorSettings",
};
const bw_EFF_USERNAME = {
    stateDefinition: {
        name: "generator",
    },
    key: "effUsernameGeneratorSettings",
};
const bw_65_migrate_forwarder_settings_SUBADDRESS = {
    stateDefinition: {
        name: "generator",
    },
    key: "subaddressGeneratorSettings",
};
const bw_ADDY_IO = {
    stateDefinition: {
        name: "generator",
    },
    key: "addyIoBuffer",
};
const bw_DUCK_DUCK_GO = {
    stateDefinition: {
        name: "generator",
    },
    key: "duckDuckGoBuffer",
};
const bw_FASTMAIL = {
    stateDefinition: {
        name: "generator",
    },
    key: "fastmailBuffer",
};
const bw_FIREFOX_RELAY = {
    stateDefinition: {
        name: "generator",
    },
    key: "firefoxRelayBuffer",
};
const bw_FORWARD_EMAIL = {
    stateDefinition: {
        name: "generator",
    },
    key: "forwardEmailBuffer",
};
const bw_SIMPLE_LOGIN = {
    stateDefinition: {
        name: "generator",
    },
    key: "simpleLoginBuffer",
};
class bw_ForwarderOptionsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_65_migrate_forwarder_settings_awaiter(this, void 0, void 0, function* () {
            const accounts = yield helper.getAccounts();
            function migrateAccount(userId, account) {
                return bw_65_migrate_forwarder_settings_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const legacyOptions = (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.usernameGenerationOptions;
                    if (legacyOptions) {
                        const converted = bw_65_migrate_forwarder_settings_convertSettings(legacyOptions);
                        yield bw_65_migrate_forwarder_settings_storeSettings(helper, userId, converted);
                        yield bw_65_migrate_forwarder_settings_deleteSettings(helper, userId, account);
                    }
                });
            }
            yield Promise.all([...accounts.map(({ userId, account }) => migrateAccount(userId, account))]);
        });
    }
    rollback(helper) {
        return bw_65_migrate_forwarder_settings_awaiter(this, void 0, void 0, function* () {
            // not supported
        });
    }
}
function bw_65_migrate_forwarder_settings_convertSettings(options) {
    const forwarders = {
        addyIo: {
            baseUrl: options.forwardedAnonAddyBaseUrl,
            token: options.forwardedAnonAddyApiToken,
            domain: options.forwardedAnonAddyDomain,
        },
        duckDuckGo: {
            token: options.forwardedDuckDuckGoToken,
        },
        fastmail: {
            token: options.forwardedFastmailApiToken,
        },
        firefoxRelay: {
            token: options.forwardedFirefoxApiToken,
        },
        forwardEmail: {
            token: options.forwardedForwardEmailApiToken,
            domain: options.forwardedForwardEmailDomain,
        },
        simpleLogin: {
            token: options.forwardedSimpleLoginApiKey,
            baseUrl: options.forwardedSimpleLoginBaseUrl,
        },
    };
    const generator = {
        username: options.type,
        forwarder: options.forwardedService,
    };
    const algorithms = {
        effUsername: {
            wordCapitalize: options.wordCapitalize,
            wordIncludeNumber: options.wordIncludeNumber,
        },
        subaddress: {
            subaddressType: options.subaddressType,
            subaddressEmail: options.subaddressEmail,
        },
        catchall: {
            catchallType: options.catchallType,
            catchallDomain: options.catchallDomain,
        },
    };
    return { generator, algorithms, forwarders };
}
function bw_65_migrate_forwarder_settings_storeSettings(helper, userId, converted) {
    return bw_65_migrate_forwarder_settings_awaiter(this, void 0, void 0, function* () {
        yield Promise.all([
            helper.setToUser(userId, bw_65_migrate_forwarder_settings_NAVIGATION, converted.generator),
            helper.setToUser(userId, bw_65_migrate_forwarder_settings_CATCHALL, converted.algorithms.catchall),
            helper.setToUser(userId, bw_EFF_USERNAME, converted.algorithms.effUsername),
            helper.setToUser(userId, bw_65_migrate_forwarder_settings_SUBADDRESS, converted.algorithms.subaddress),
            helper.setToUser(userId, bw_ADDY_IO, converted.forwarders.addyIo),
            helper.setToUser(userId, bw_DUCK_DUCK_GO, converted.forwarders.duckDuckGo),
            helper.setToUser(userId, bw_FASTMAIL, converted.forwarders.fastmail),
            helper.setToUser(userId, bw_FIREFOX_RELAY, converted.forwarders.firefoxRelay),
            helper.setToUser(userId, bw_FORWARD_EMAIL, converted.forwarders.forwardEmail),
            helper.setToUser(userId, bw_SIMPLE_LOGIN, converted.forwarders.simpleLogin),
        ]);
    });
}
function bw_65_migrate_forwarder_settings_deleteSettings(helper, userId, account) {
    return bw_65_migrate_forwarder_settings_awaiter(this, void 0, void 0, function* () {
        var _a;
        (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? true : delete _a.usernameGenerationOptions;
        yield helper.set(userId, account);
    });
}

;// ../../libs/common/src/state-migrations/migrations/66-move-final-desktop-settings.ts
var bw_66_move_final_desktop_settings_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_66_move_final_desktop_settings_DESKTOP_SETTINGS_DISK = {
    name: "desktopSettings",
};
const bw_BROWSER_INTEGRATION_ENABLED = {
    key: "browserIntegrationEnabled",
    stateDefinition: bw_66_move_final_desktop_settings_DESKTOP_SETTINGS_DISK,
};
const bw_BROWSER_INTEGRATION_FINGERPRINT_ENABLED = {
    key: "browserIntegrationFingerprintEnabled",
    stateDefinition: bw_66_move_final_desktop_settings_DESKTOP_SETTINGS_DISK,
};
const bw_MINIMIZE_ON_COPY = {
    key: "minimizeOnCopy",
    stateDefinition: bw_66_move_final_desktop_settings_DESKTOP_SETTINGS_DISK,
};
class bw_MoveFinalDesktopSettingsMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_66_move_final_desktop_settings_awaiter(this, void 0, void 0, function* () {
            const legacyGlobal = yield helper.get("global");
            const enableBrowserIntegrationValue = legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableBrowserIntegration;
            const enableBrowserIntegrationFingerprintValue = legacyGlobal === null || legacyGlobal === void 0 ? void 0 : legacyGlobal.enableBrowserIntegrationFingerprint;
            let updatedGlobal = false;
            if (enableBrowserIntegrationValue != null) {
                yield helper.setToGlobal(bw_BROWSER_INTEGRATION_ENABLED, enableBrowserIntegrationValue);
                delete legacyGlobal.enableBrowserIntegration;
                updatedGlobal = true;
            }
            if (enableBrowserIntegrationFingerprintValue != null) {
                yield helper.setToGlobal(bw_BROWSER_INTEGRATION_FINGERPRINT_ENABLED, enableBrowserIntegrationFingerprintValue);
                delete legacyGlobal.enableBrowserIntegrationFingerprint;
                updatedGlobal = true;
            }
            if (updatedGlobal) {
                yield helper.set("global", legacyGlobal);
            }
            function migrateAccount(userId, account) {
                return bw_66_move_final_desktop_settings_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const minimizeOnCopyToClipboardValue = (_a = account === null || account === void 0 ? void 0 : account.settings) === null || _a === void 0 ? void 0 : _a.minimizeOnCopyToClipboard;
                    if (minimizeOnCopyToClipboardValue != null) {
                        yield helper.setToUser(userId, bw_MINIMIZE_ON_COPY, minimizeOnCopyToClipboardValue);
                        delete account.settings.minimizeOnCopyToClipboard;
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => migrateAccount(userId, account)));
        });
    }
    rollback(helper) {
        return bw_66_move_final_desktop_settings_awaiter(this, void 0, void 0, function* () {
            const browserIntegrationEnabledValue = yield helper.getFromGlobal(bw_BROWSER_INTEGRATION_ENABLED);
            const browserIntegrationFingerprintEnabled = yield helper.getFromGlobal(bw_BROWSER_INTEGRATION_FINGERPRINT_ENABLED);
            if (browserIntegrationEnabledValue != null) {
                let legacyGlobal = yield helper.get("global");
                legacyGlobal !== null && legacyGlobal !== void 0 ? legacyGlobal : (legacyGlobal = {});
                legacyGlobal.enableBrowserIntegration = browserIntegrationEnabledValue;
                yield helper.set("global", legacyGlobal);
                yield helper.removeFromGlobal(bw_BROWSER_INTEGRATION_ENABLED);
            }
            if (browserIntegrationFingerprintEnabled != null) {
                let legacyGlobal = yield helper.get("global");
                legacyGlobal !== null && legacyGlobal !== void 0 ? legacyGlobal : (legacyGlobal = {});
                legacyGlobal.enableBrowserIntegrationFingerprint = browserIntegrationFingerprintEnabled;
                yield helper.set("global", legacyGlobal);
                yield helper.removeFromGlobal(bw_BROWSER_INTEGRATION_FINGERPRINT_ENABLED);
            }
            function rollbackAccount(userId, account) {
                return bw_66_move_final_desktop_settings_awaiter(this, void 0, void 0, function* () {
                    const minimizeOnCopyToClipboardValue = yield helper.getFromUser(userId, bw_MINIMIZE_ON_COPY);
                    if (minimizeOnCopyToClipboardValue != null) {
                        account !== null && account !== void 0 ? account : (account = { settings: {} });
                        account.settings.minimizeOnCopyToClipboard = minimizeOnCopyToClipboardValue;
                        yield helper.set(userId, account);
                        yield helper.removeFromUser(userId, bw_MINIMIZE_ON_COPY);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackAccount(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/67-remove-unassigned-items-banner-dismissed.ts
var bw_67_remove_unassigned_items_banner_dismissed_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_SHOW_BANNER = {
    key: "showBanner",
    stateDefinition: { name: "unassignedItemsBanner" },
};
class bw_RemoveUnassignedItemsBannerDismissed extends bw_Migrator {
    migrate(helper) {
        return bw_67_remove_unassigned_items_banner_dismissed_awaiter(this, void 0, void 0, function* () {
            yield Promise.all((yield helper.getAccounts()).map((_a) => bw_67_remove_unassigned_items_banner_dismissed_awaiter(this, [_a], void 0, function* ({ userId }) {
                if (helper.getFromUser(userId, bw_SHOW_BANNER) != null) {
                    yield helper.removeFromUser(userId, bw_SHOW_BANNER);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_67_remove_unassigned_items_banner_dismissed_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/68-move-last-sync-date.ts
var bw_68_move_last_sync_date_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_68_move_last_sync_date_LAST_SYNC_KEY = {
    key: "lastSync",
    stateDefinition: {
        name: "sync",
    },
};
class bw_MoveLastSyncDate extends bw_Migrator {
    migrate(helper) {
        return bw_68_move_last_sync_date_awaiter(this, void 0, void 0, function* () {
            function migrateAccount(userId, account) {
                return bw_68_move_last_sync_date_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = (_a = account === null || account === void 0 ? void 0 : account.profile) === null || _a === void 0 ? void 0 : _a.lastSync;
                    if (value != null) {
                        yield helper.setToUser(userId, bw_68_move_last_sync_date_LAST_SYNC_KEY, value);
                        delete account.profile.lastSync;
                        yield helper.set(userId, account);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => migrateAccount(userId, account)));
        });
    }
    rollback(helper) {
        return bw_68_move_last_sync_date_awaiter(this, void 0, void 0, function* () {
            function rollbackAccount(userId, account) {
                return bw_68_move_last_sync_date_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    const value = yield helper.getFromUser(userId, bw_68_move_last_sync_date_LAST_SYNC_KEY);
                    if (value != null) {
                        account !== null && account !== void 0 ? account : (account = {});
                        (_a = account.profile) !== null && _a !== void 0 ? _a : (account.profile = {});
                        account.profile.lastSync = value;
                        yield helper.set(userId, account);
                        yield helper.removeFromUser(userId, bw_68_move_last_sync_date_LAST_SYNC_KEY);
                    }
                });
            }
            const accounts = yield helper.getAccounts();
            yield Promise.all(accounts.map(({ userId, account }) => rollbackAccount(userId, account)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/69-migrate-incorrect-folder-key.ts
var bw_69_migrate_incorrect_folder_key_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_BAD_FOLDER_KEY = {
    key: "folder", // We inadvertently changed the key from "folders" to "folder"
    stateDefinition: {
        name: "folder",
    },
};
const bw_GOOD_FOLDER_KEY = {
    key: "folders", // We should keep the key as "folders"
    stateDefinition: {
        name: "folder",
    },
};
class bw_MigrateIncorrectFolderKey extends bw_Migrator {
    migrate(helper) {
        return bw_69_migrate_incorrect_folder_key_awaiter(this, void 0, void 0, function* () {
            function migrateUser(userId) {
                return bw_69_migrate_incorrect_folder_key_awaiter(this, void 0, void 0, function* () {
                    const value = yield helper.getFromUser(userId, bw_BAD_FOLDER_KEY);
                    if (value != null) {
                        yield helper.setToUser(userId, bw_GOOD_FOLDER_KEY, value);
                    }
                    yield helper.removeFromUser(userId, bw_BAD_FOLDER_KEY);
                });
            }
            const users = yield helper.getKnownUserIds();
            yield Promise.all(users.map((userId) => migrateUser(userId)));
        });
    }
    rollback(helper) {
        return bw_69_migrate_incorrect_folder_key_awaiter(this, void 0, void 0, function* () {
            function rollbackUser(userId) {
                return bw_69_migrate_incorrect_folder_key_awaiter(this, void 0, void 0, function* () {
                    const value = yield helper.getFromUser(userId, bw_GOOD_FOLDER_KEY);
                    if (value != null) {
                        yield helper.setToUser(userId, bw_BAD_FOLDER_KEY, value);
                    }
                    yield helper.removeFromUser(userId, bw_GOOD_FOLDER_KEY);
                });
            }
            const users = yield helper.getKnownUserIds();
            yield Promise.all(users.map((userId) => rollbackUser(userId)));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/7-move-biometric-auto-prompt-to-account.ts
var bw_7_move_biometric_auto_prompt_to_account_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_MoveBiometricAutoPromptToAccount extends bw_Migrator {
    migrate(helper) {
        return bw_7_move_biometric_auto_prompt_to_account_awaiter(this, void 0, void 0, function* () {
            var _a;
            const global = yield helper.get("global");
            const noAutoPromptBiometrics = (_a = global === null || global === void 0 ? void 0 : global.noAutoPromptBiometrics) !== null && _a !== void 0 ? _a : false;
            const accounts = yield helper.getAccounts();
            function updateAccount(userId, account) {
                return bw_7_move_biometric_auto_prompt_to_account_awaiter(this, void 0, void 0, function* () {
                    var _a;
                    if (account == null) {
                        return;
                    }
                    if (noAutoPromptBiometrics) {
                        account.settings = Object.assign((_a = account === null || account === void 0 ? void 0 : account.settings) !== null && _a !== void 0 ? _a : {}, {
                            disableAutoBiometricsPrompt: true,
                        });
                        yield helper.set(userId, account);
                    }
                });
            }
            delete global.noAutoPromptBiometrics;
            yield Promise.all([
                ...accounts.map(({ userId, account }) => updateAccount(userId, account)),
                helper.set("global", global),
            ]);
        });
    }
    rollback(helper) {
        return bw_7_move_biometric_auto_prompt_to_account_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
    // Override is necessary because default implementation assumes `stateVersion` at the root, but for this version
    // it is nested inside a global object.
    updateVersion(helper, direction) {
        return bw_7_move_biometric_auto_prompt_to_account_awaiter(this, void 0, void 0, function* () {
            const endVersion = direction === "up" ? this.toVersion : this.fromVersion;
            helper.currentVersion = endVersion;
            const global = (yield helper.get("global")) || {};
            yield helper.set("global", Object.assign(Object.assign({}, global), { stateVersion: endVersion }));
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/70-remove-ac-banner-dismissed.ts
var bw_70_remove_ac_banner_dismissed_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

const bw_SHOW_BANNER_KEY = {
    key: "acBannersDismissed",
    stateDefinition: { name: "showProviderClientVaultPrivacyBanner" },
};
class bw_RemoveAcBannersDismissed extends bw_Migrator {
    migrate(helper) {
        return bw_70_remove_ac_banner_dismissed_awaiter(this, void 0, void 0, function* () {
            yield Promise.all((yield helper.getAccounts()).map((_a) => bw_70_remove_ac_banner_dismissed_awaiter(this, [_a], void 0, function* ({ userId }) {
                if (helper.getFromUser(userId, bw_SHOW_BANNER_KEY) != null) {
                    yield helper.removeFromUser(userId, bw_SHOW_BANNER_KEY);
                }
            })));
        });
    }
    rollback(helper) {
        return bw_70_remove_ac_banner_dismissed_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/8-move-state-version.ts
var bw_8_move_state_version_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_MoveStateVersionMigrator extends bw_Migrator {
    migrate(helper) {
        return bw_8_move_state_version_awaiter(this, void 0, void 0, function* () {
            const global = yield helper.get("global");
            if (global.stateVersion) {
                yield helper.set("stateVersion", global.stateVersion);
                delete global.stateVersion;
                yield helper.set("global", global);
            }
            else {
                throw new Error("Migration failed, state version not found");
            }
        });
    }
    rollback(helper) {
        return bw_8_move_state_version_awaiter(this, void 0, void 0, function* () {
            const version = yield helper.get("stateVersion");
            const global = yield helper.get("global");
            yield helper.set("global", Object.assign(Object.assign({}, global), { stateVersion: version }));
            yield helper.set("stateVersion", undefined);
        });
    }
    // Override is necessary because default implementation assumes `stateVersion` at the root, but this migration moves
    // it from a `global` object to root.This makes for unique rollback versioning.
    updateVersion(helper, direction) {
        return bw_8_move_state_version_awaiter(this, void 0, void 0, function* () {
            const endVersion = direction === "up" ? this.toVersion : this.fromVersion;
            helper.currentVersion = endVersion;
            if (direction === "up") {
                yield helper.set("stateVersion", endVersion);
            }
            else {
                const global = (yield helper.get("global")) || {};
                yield helper.set("global", Object.assign(Object.assign({}, global), { stateVersion: endVersion }));
            }
        });
    }
}

;// ../../libs/common/src/state-migrations/migrations/9-move-browser-settings-to-global.ts
var bw_9_move_browser_settings_to_global_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_MoveBrowserSettingsToGlobal extends bw_Migrator {
    // Will first check if any of the accounts have a value from the given accountSelector
    // if they do have a value it will set that value into global state but if multiple
    // users have differing values it will prefer the false setting,
    // if all users have true then it will take true.
    tryAddSetting(accounts, accountSelector, globalSetter) {
        const hasValue = accounts.some(({ account }) => {
            return accountSelector(account) !== undefined;
        });
        if (hasValue) {
            const value = !accounts.some(({ account }) => {
                var _a;
                return ((_a = accountSelector(account)) !== null && _a !== void 0 ? _a : false) === false;
            });
            globalSetter(value);
        }
    }
    migrate(helper) {
        return bw_9_move_browser_settings_to_global_awaiter(this, void 0, void 0, function* () {
            const global = yield helper.get("global");
            const accounts = yield helper.getAccounts();
            const globalNeverDomainsValue = accounts.reduce((accumulator, { account }) => {
                var _a, _b;
                const normalizedNeverDomains = (_b = (_a = account.settings) === null || _a === void 0 ? void 0 : _a.neverDomains) !== null && _b !== void 0 ? _b : {};
                for (const [id, value] of Object.entries(normalizedNeverDomains)) {
                    accumulator !== null && accumulator !== void 0 ? accumulator : (accumulator = {});
                    accumulator[id] = value;
                }
                return accumulator;
            }, undefined);
            const targetGlobalState = {};
            if (globalNeverDomainsValue != null) {
                targetGlobalState.neverDomains = globalNeverDomainsValue;
            }
            this.tryAddSetting(accounts, (a) => { var _a; return (_a = a.settings) === null || _a === void 0 ? void 0 : _a.disableAddLoginNotification; }, (v) => (targetGlobalState.disableAddLoginNotification = v));
            this.tryAddSetting(accounts, (a) => { var _a; return (_a = a.settings) === null || _a === void 0 ? void 0 : _a.disableChangedPasswordNotification; }, (v) => (targetGlobalState.disableChangedPasswordNotification = v));
            this.tryAddSetting(accounts, (a) => { var _a; return (_a = a.settings) === null || _a === void 0 ? void 0 : _a.disableContextMenuItem; }, (v) => (targetGlobalState.disableContextMenuItem = v));
            yield helper.set("global", Object.assign(Object.assign({}, global), targetGlobalState));
            yield Promise.all(accounts.map((_a) => bw_9_move_browser_settings_to_global_awaiter(this, [_a], void 0, function* ({ userId, account }) {
                var _b, _c, _d, _e;
                (_b = account.settings) === null || _b === void 0 ? true : delete _b.disableAddLoginNotification;
                (_c = account.settings) === null || _c === void 0 ? true : delete _c.disableChangedPasswordNotification;
                (_d = account.settings) === null || _d === void 0 ? true : delete _d.disableContextMenuItem;
                (_e = account.settings) === null || _e === void 0 ? true : delete _e.neverDomains;
                yield helper.set(userId, account);
            })));
        });
    }
    rollback(helper) {
        throw new Error("Method not implemented.");
    }
}

;// ../../libs/common/src/state-migrations/migrations/min-version.ts
var bw_min_version_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


function bw_minVersionError(current) {
    return `Your local data is too old to be migrated. Your current state version is ${current}, but minimum version is ${bw_MIN_VERSION}.`;
}
class bw_MinVersionMigrator extends bw_Migrator {
    constructor() {
        super(0, bw_MIN_VERSION);
    }
    // Overrides the default implementation to catch any version that may be passed in.
    shouldMigrate(helper) {
        return Promise.resolve(helper.currentVersion < bw_MIN_VERSION);
    }
    migrate(helper) {
        return bw_min_version_awaiter(this, void 0, void 0, function* () {
            if (helper.currentVersion < bw_MIN_VERSION) {
                throw new Error(bw_minVersionError(helper.currentVersion));
            }
        });
    }
    rollback(helper) {
        return bw_min_version_awaiter(this, void 0, void 0, function* () {
            throw bw_IRREVERSIBLE;
        });
    }
}

;// ../../libs/common/src/state-migrations/migrate.ts
var bw_migrate_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};





































































const bw_MIN_VERSION = 3;
const bw_CURRENT_VERSION = 70;
function bw_createMigrationBuilder() {
    return bw_MigrationBuilder.create()
        .with(bw_MinVersionMigrator)
        .with(bw_RemoveEverBeenUnlockedMigrator, 3, 4)
        .with(bw_AddKeyTypeToOrgKeysMigrator, 4, 5)
        .with(bw_RemoveLegacyEtmKeyMigrator, 5, 6)
        .with(bw_MoveBiometricAutoPromptToAccount, 6, 7)
        .with(bw_MoveStateVersionMigrator, 7, 8)
        .with(bw_MoveBrowserSettingsToGlobal, 8, 9)
        .with(bw_EverHadUserKeyMigrator, 9, 10)
        .with(bw_OrganizationKeyMigrator, 10, 11)
        .with(bw_MoveEnvironmentStateToProviders, 11, 12)
        .with(bw_ProviderKeyMigrator, 12, 13)
        .with(bw_MoveBiometricClientKeyHalfToStateProviders, 13, 14)
        .with(bw_FolderMigrator, 14, 15)
        .with(bw_LastSyncMigrator, 15, 16)
        .with(bw_EnablePasskeysMigrator, 16, 17)
        .with(bw_AutofillSettingsKeyMigrator, 17, 18)
        .with(bw_RequirePasswordOnStartMigrator, 18, 19)
        .with(bw_PrivateKeyMigrator, 19, 20)
        .with(bw_CollectionMigrator, 20, 21)
        .with(bw_CollapsedGroupingsMigrator, 21, 22)
        .with(bw_MoveBiometricPromptsToStateProviders, 22, 23)
        .with(bw_SmOnboardingTasksMigrator, 23, 24)
        .with(bw_ClearClipboardDelayMigrator, 24, 25)
        .with(bw_RevertLastSyncMigrator, 25, 26)
        .with(bw_BadgeSettingsMigrator, 26, 27)
        .with(bw_MoveBiometricUnlockToStateProviders, 27, 28)
        .with(bw_UserNotificationSettingsKeyMigrator, 28, 29)
        .with(bw_PolicyMigrator, 29, 30)
        .with(bw_EnableContextMenuMigrator, 30, 31)
        .with(bw_PreferredLanguageMigrator, 31, 32)
        .with(bw_AppIdMigrator, 32, 33)
        .with(bw_DomainSettingsMigrator, 33, 34)
        .with(bw_MoveThemeToStateProviderMigrator, 34, 35)
        .with(bw_VaultSettingsKeyMigrator, 35, 36)
        .with(bw_AvatarColorMigrator, 36, 37)
        .with(bw_TokenServiceStateProviderMigrator, 37, 38)
        .with(bw_MoveBillingAccountProfileMigrator, 38, 39)
        .with(bw_OrganizationMigrator, 39, 40)
        .with(bw_EventCollectionMigrator, 40, 41)
        .with(bw_EnableFaviconMigrator, 41, 42)
        .with(bw_AutoConfirmFingerPrintsMigrator, 42, 43)
        .with(bw_UserDecryptionOptionsMigrator, 43, 44)
        .with(bw_MergeEnvironmentState, 44, 45)
        .with(bw_DeleteBiometricPromptCancelledData, 45, 46)
        .with(bw_MoveDesktopSettingsMigrator, 46, 47)
        .with(bw_MoveDdgToStateProviderMigrator, 47, 48)
        .with(bw_AccountServerConfigMigrator, 48, 49)
        .with(bw_KeyConnectorMigrator, 49, 50)
        .with(bw_RememberedEmailMigrator, 50, 51)
        .with(bw_DeleteInstalledVersion, 51, 52)
        .with(bw_DeviceTrustServiceStateProviderMigrator, 52, 53)
        .with(bw_SendMigrator, 53, 54)
        .with(bw_MoveMasterKeyStateToProviderMigrator, 54, 55)
        .with(bw_AuthRequestMigrator, 55, 56)
        .with(bw_CipherServiceMigrator, 56, 57)
        .with(bw_RemoveRefreshTokenMigratedFlagMigrator, 57, 58)
        .with(bw_KdfConfigMigrator, 58, 59)
        .with(bw_KnownAccountsMigrator, 59, 60)
        .with(bw_PinStateMigrator, 60, 61)
        .with(bw_VaultTimeoutSettingsServiceStateProviderMigrator, 61, 62)
        .with(bw_PasswordOptionsMigrator, 62, 63)
        .with(bw_GeneratorHistoryMigrator, 63, 64)
        .with(bw_ForwarderOptionsMigrator, 64, 65)
        .with(bw_MoveFinalDesktopSettingsMigrator, 65, 66)
        .with(bw_RemoveUnassignedItemsBannerDismissed, 66, 67)
        .with(bw_MoveLastSyncDate, 67, 68)
        .with(bw_MigrateIncorrectFolderKey, 68, 69)
        .with(bw_RemoveAcBannersDismissed, 69, bw_CURRENT_VERSION);
}
function bw_currentVersion(storageService, logService) {
    return bw_migrate_awaiter(this, void 0, void 0, function* () {
        var _a;
        let state = yield storageService.get("stateVersion");
        if (state == null) {
            // Pre v8
            state = (_a = (yield storageService.get("global"))) === null || _a === void 0 ? void 0 : _a.stateVersion;
        }
        if (state == null) {
            logService.info("No state version found, assuming empty state.");
            return -1;
        }
        logService.info(`State version: ${state}`);
        return state;
    });
}
/**
 * Waits for migrations to have a chance to run and will resolve the promise once they are.
 *
 * @param storageService Disk storage where the `stateVersion` will or is already saved in.
 * @param logService Log service
 */
function bw_waitForMigrations(storageService, logService) {
    return bw_migrate_awaiter(this, void 0, void 0, function* () {
        const isReady = () => bw_migrate_awaiter(this, void 0, void 0, function* () {
            const version = yield bw_currentVersion(storageService, logService);
            // The saved version is what we consider the latest
            // migrations should be complete, the state version
            // shouldn't become larger than `CURRENT_VERSION` in
            // any normal usage of the application but it is common
            // enough in dev scenarios where we want to consider that
            // ready as well and return true in that scenario.
            return version >= bw_CURRENT_VERSION;
        });
        const wait = (time) => bw_migrate_awaiter(this, void 0, void 0, function* () {
            // Wait exponentially
            const nextTime = time * 2;
            if (nextTime > 8192) {
                // Don't wait longer than ~8 seconds in a single wait,
                // if the migrations still haven't happened. They aren't
                // likely to.
                return;
            }
            return new Promise((resolve) => {
                setTimeout(() => bw_migrate_awaiter(this, void 0, void 0, function* () {
                    if (!(yield isReady())) {
                        logService.info(`Waiting for migrations to finish, waiting for ${nextTime}ms`);
                        yield wait(nextTime);
                    }
                    resolve();
                }), time);
            });
        });
        if (!(yield isReady())) {
            // Wait for 2ms to start with
            yield wait(2);
        }
    });
}

;// ../../libs/common/src/state-migrations/index.ts


;// ../../libs/common/src/platform/services/migration-builder.service.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_MigrationBuilderService {
    build() {
        var _a;
        return ((_a = this.migrationBuilderCache) !== null && _a !== void 0 ? _a : (this.migrationBuilderCache = bw_createMigrationBuilder()));
    }
}

;// ../../libs/common/src/state-migrations/migration-helper.ts
var bw_migration_helper_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_MigrationHelper {
    constructor(currentVersion, storageService, logService, type, clientType) {
        this.currentVersion = currentVersion;
        this.storageService = storageService;
        this.logService = logService;
        this.clientType = clientType;
        this.type = type;
    }
    /**
     * Gets a value from the storage service at the given key.
     *
     * This is a brute force method to just get a value from the storage service. If you can use {@link getFromGlobal} or {@link getFromUser}, you should.
     * @param key location
     * @returns the value at the location
     */
    get(key) {
        return this.storageService.get(key);
    }
    /**
     * Sets a value in the storage service at the given key.
     *
     * This is a brute force method to just set a value in the storage service. If you can use {@link setToGlobal} or {@link setToUser}, you should.
     * @param key location
     * @param value the value to set
     * @returns
     */
    set(key, value) {
        this.logService.info(`Setting ${key}`);
        return this.storageService.save(key, value);
    }
    /**
     * Remove a value in the storage service at the given key.
     *
     * This is a brute force method to just remove a value in the storage service. If you can use {@link removeFromGlobal} or {@link removeFromUser}, you should.
     * @param key location
     * @returns void
     */
    remove(key) {
        this.logService.info(`Removing ${key}`);
        return this.storageService.remove(key);
    }
    /**
     * Gets a globally scoped value from a location derived through the key definition
     *
     * This is for use with the state providers framework, DO NOT use for values stored with {@link StateService},
     * use {@link get} for those.
     * @param keyDefinition unique key definition
     * @returns value from store
     */
    getFromGlobal(keyDefinition) {
        return this.get(this.getGlobalKey(keyDefinition));
    }
    /**
     * Sets a globally scoped value to a location derived through the key definition
     *
     * This is for use with the state providers framework, DO NOT use for values stored with {@link StateService},
     * use {@link set} for those.
     * @param keyDefinition unique key definition
     * @param value value to store
     * @returns void
     */
    setToGlobal(keyDefinition, value) {
        return this.set(this.getGlobalKey(keyDefinition), value);
    }
    /**
     * Remove a globally scoped location derived through the key definition
     *
     * This is for use with the state providers framework, DO NOT use for values stored with {@link StateService},
     * use {@link remove} for those.
     * @param keyDefinition unique key definition
     * @returns void
     */
    removeFromGlobal(keyDefinition) {
        return this.remove(this.getGlobalKey(keyDefinition));
    }
    /**
     * Gets a user scoped value from a location derived through the user id and key definition
     *
     * This is for use with the state providers framework, DO NOT use for values stored with {@link StateService},
     * use {@link get} for those.
     * @param userId userId to use in the key
     * @param keyDefinition unique key definition
     * @returns value from store
     */
    getFromUser(userId, keyDefinition) {
        return this.get(this.getUserKey(userId, keyDefinition));
    }
    /**
     * Sets a user scoped value to a location derived through the user id and key definition
     *
     * This is for use with the state providers framework, DO NOT use for values stored with {@link StateService},
     * use {@link set} for those.
     * @param userId userId to use in the key
     * @param keyDefinition unique key definition
     * @param value value to store
     * @returns void
     */
    setToUser(userId, keyDefinition, value) {
        return this.set(this.getUserKey(userId, keyDefinition), value);
    }
    /**
     * Remove a user scoped location derived through the key definition
     *
     * This is for use with the state providers framework, DO NOT use for values stored with {@link StateService},
     * use {@link remove} for those.
     * @param keyDefinition unique key definition
     * @returns void
     */
    removeFromUser(userId, keyDefinition) {
        return this.remove(this.getUserKey(userId, keyDefinition));
    }
    info(message) {
        this.logService.info(message);
    }
    /**
     * Helper method to read all Account objects stored by the State Service.
     *
     * This is useful from creating migrations off of this paradigm, but should not be used once a value is migrated to a state provider.
     *
     * @returns a list of all accounts that have been authenticated with state service, cast the expected type.
     */
    getAccounts() {
        return bw_migration_helper_awaiter(this, void 0, void 0, function* () {
            const userIds = yield this.getKnownUserIds();
            return Promise.all(userIds.map((userId) => bw_migration_helper_awaiter(this, void 0, void 0, function* () {
                return ({
                    userId,
                    account: yield this.get(userId),
                });
            })));
        });
    }
    /**
     * Helper method to read known users ids.
     */
    getKnownUserIds() {
        return bw_migration_helper_awaiter(this, void 0, void 0, function* () {
            if (this.currentVersion < 60) {
                return bw_knownAccountUserIdsBuilderPre60(this.storageService);
            }
            else {
                return bw_knownAccountUserIdsBuilder(this.storageService);
            }
        });
    }
    /**
     * Builds a user storage key appropriate for the current version.
     *
     * @param userId userId to use in the key
     * @param keyDefinition state and key to use in the key
     * @returns
     */
    getUserKey(userId, keyDefinition) {
        if (this.currentVersion < 9) {
            return bw_userKeyBuilderPre9();
        }
        else {
            return bw_userKeyBuilder(userId, keyDefinition);
        }
    }
    /**
     * Builds a global storage key appropriate for the current version.
     *
     * @param keyDefinition state and key to use in the key
     * @returns
     */
    getGlobalKey(keyDefinition) {
        if (this.currentVersion < 9) {
            return bw_globalKeyBuilderPre9();
        }
        else {
            return bw_migration_helper_globalKeyBuilder(keyDefinition);
        }
    }
}
/**
 * When this is updated, rename this function to `userKeyBuilderXToY` where `X` is the version number it
 * became relevant, and `Y` prior to the version it was updated.
 *
 * Be sure to update the map in `MigrationHelper` to point to the appropriate function for the current version.
 * @param userId The userId of the user you want the key to be for.
 * @param keyDefinition the key definition of which data the key should point to.
 * @returns
 */
function bw_userKeyBuilder(userId, keyDefinition) {
    return `user_${userId}_${keyDefinition.stateDefinition.name}_${keyDefinition.key}`;
}
function bw_userKeyBuilderPre9() {
    throw Error("No key builder should be used for versions prior to 9.");
}
/**
 * When this is updated, rename this function to `globalKeyBuilderXToY` where `X` is the version number
 * it became relevant, and `Y` prior to the version it was updated.
 *
 * Be sure to update the map in `MigrationHelper` to point to the appropriate function for the current version.
 * @param keyDefinition the key definition of which data the key should point to.
 * @returns
 */
function bw_migration_helper_globalKeyBuilder(keyDefinition) {
    return `global_${keyDefinition.stateDefinition.name}_${keyDefinition.key}`;
}
function bw_globalKeyBuilderPre9() {
    throw Error("No key builder should be used for versions prior to 9.");
}
function bw_knownAccountUserIdsBuilderPre60(storageService) {
    return bw_migration_helper_awaiter(this, void 0, void 0, function* () {
        var _a;
        return (_a = (yield storageService.get("authenticatedAccounts"))) !== null && _a !== void 0 ? _a : [];
    });
}
function bw_knownAccountUserIdsBuilder(storageService) {
    return bw_migration_helper_awaiter(this, void 0, void 0, function* () {
        const accounts = yield storageService.get(bw_migration_helper_globalKeyBuilder({ stateDefinition: { name: "account" }, key: "accounts" }));
        return Object.keys(accounts !== null && accounts !== void 0 ? accounts : {});
    });
}

;// ../../libs/common/src/platform/services/migration-runner.ts
var bw_migration_runner_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_MigrationRunner {
    constructor(diskStorage, logService, migrationBuilderService, clientType) {
        this.diskStorage = diskStorage;
        this.logService = logService;
        this.migrationBuilderService = migrationBuilderService;
        this.clientType = clientType;
    }
    run() {
        return bw_migration_runner_awaiter(this, void 0, void 0, function* () {
            const migrationHelper = new bw_MigrationHelper(yield bw_currentVersion(this.diskStorage, this.logService), this.diskStorage, this.logService, "general", this.clientType);
            if (migrationHelper.currentVersion < 0) {
                // Cannot determine state, assuming empty so we don't repeatedly apply a migration.
                yield this.diskStorage.save("stateVersion", bw_CURRENT_VERSION);
                return;
            }
            const migrationBuilder = this.migrationBuilderService.build();
            yield migrationBuilder.migrate(migrationHelper);
        });
    }
    waitForCompletion() {
        return bw_migration_runner_awaiter(this, void 0, void 0, function* () {
            yield bw_waitForMigrations(this.diskStorage, this.logService);
        });
    }
}

;// ../../libs/common/src/platform/services/sdk/default-sdk-client-factory.ts
var bw_default_sdk_client_factory_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

/**
 * Default SDK client factory.
 */
class bw_DefaultSdkClientFactory {
    /**
     * Initializes a Bitwarden client. Assumes the SDK is already loaded.
     * @param args Bitwarden client constructor parameters
     * @returns A BitwardenClient
     */
    createSdkClient(...args) {
        return bw_default_sdk_client_factory_awaiter(this, void 0, void 0, function* () {
            return Promise.resolve(new bw_bitwarden_wasm_internal_bg/* BitwardenClient */.g(...args));
        });
    }
}

;// ../../libs/common/src/platform/abstractions/sdk/sdk-load.service.ts
var bw_sdk_load_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_SdkLoadFailedError extends Error {
    constructor(error) {
        super(`SDK loading failed: ${error}`);
    }
}
class bw_SdkLoadService {
    /**
     * Load WASM and initalize SDK-JS integrations such as logging.
     * This method should be called once at the start of the application.
     * Raw functions and classes from the SDK can be used after this method resolves.
     */
    loadAndInit() {
        return bw_sdk_load_service_awaiter(this, void 0, void 0, function* () {
            try {
                yield this.load();
                (0,bw_bitwarden_wasm_internal_bg/* init_sdk */.Ge)();
                bw_SdkLoadService.markAsReady();
            }
            catch (error) {
                bw_SdkLoadService.markAsFailed(error);
            }
        });
    }
}
/**
 * This promise is resolved when the SDK is ready to be used. Use it when your code might run early and/or is not able to use DI.
 * Beware that WASM always requires a load step which makes it tricky to use functions and classes directly, it is therefore recommended
 * to use the SDK through the {@link SdkService}. Only use this promise in advanced scenarios!
 *
 * @example
 * ```typescript
 * import { pureFunction } from "@bitwarden/sdk-internal";
 *
 * async function myFunction() {
 *   await SdkLoadService.Ready;
 *   pureFunction();
 * }
 * ```
 */
bw_SdkLoadService.Ready = new Promise((resolve, reject) => {
    bw_SdkLoadService.markAsReady = resolve;
    bw_SdkLoadService.markAsFailed = (error) => reject(new bw_SdkLoadFailedError(error));
});

;// ../../libs/common/src/platform/abstractions/sdk/sdk.service.ts
class bw_UserNotLoggedInError extends Error {
    constructor(userId) {
        super(`User (${userId}) is not logged in`);
    }
}
class bw_SdkService {
}

;// ../../libs/common/src/platform/misc/compare-values.ts
/**
 * Performs deep equality check between two values
 *
 * NOTE: This method uses JSON.stringify to compare objects, which may return false
 * for objects with the same properties but in different order. If order-insensitive
 * comparison becomes necessary in future, consider updating this method to use a comparison
 * that checks for property existence and value equality without regard to order.
 */
function bw_compareValues(value1, value2) {
    if (value1 == null && value2 == null) {
        return true;
    }
    if (value1 && value2 == null) {
        return false;
    }
    if (value1 == null && value2) {
        return false;
    }
    if (typeof value1 !== "object" || typeof value2 !== "object") {
        return value1 === value2;
    }
    return JSON.stringify(value1) === JSON.stringify(value2);
}

;// ../../libs/common/src/platform/misc/reference-counting/rc.ts
/**
 * Reference counted disposable value.
 * This class is used to manage the lifetime of a value that needs to be
 * freed of at a specific time but might still be in-use when that happens.
 */
class bw_Rc {
    constructor(value) {
        this.markedForDisposal = false;
        this.refCount = 0;
        this.value = value;
    }
    /**
     * Use this function when you want to use the underlying object.
     * This will guarantee that you have a reference to the object
     * and that it won't be freed until your reference goes out of scope.
     *
     * This function must be used with the `using` keyword.
     *
     * @example
     * ```typescript
     * function someFunction(rc: Rc<SomeValue>) {
     *   using reference = rc.take();
     *   reference.value.doSomething();
     *   // reference is automatically disposed here
     * }
     * ```
     *
     * @returns The value.
     */
    take() {
        if (this.markedForDisposal) {
            throw new Error("Cannot take a reference to a value marked for disposal");
        }
        this.refCount++;
        return new bw_Ref(() => this.release(), this.value);
    }
    /**
     * Mark this Rc for disposal. When the refCount reaches 0, the value
     * will be freed.
     */
    markForDisposal() {
        this.markedForDisposal = true;
        this.freeIfPossible();
    }
    release() {
        this.refCount--;
        this.freeIfPossible();
    }
    freeIfPossible() {
        if (this.refCount === 0 && this.markedForDisposal) {
            this.value.free();
        }
    }
}
class bw_Ref {
    constructor(release, value) {
        this.release = release;
        this.value = value;
    }
    [Symbol.dispose]() {
        this.release();
    }
}

;// ../../libs/common/src/platform/services/sdk/default-sdk.service.ts
var bw_default_sdk_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};







// A symbol that represents an overriden client that is explicitly set to undefined,
// blocking the creation of an internal client for that user.
const bw_UnsetClient = Symbol("UnsetClient");
class bw_DefaultSdkService {
    constructor(sdkClientFactory, environmentService, platformUtilsService, accountService, kdfConfigService, keyService, userAgent = null) {
        this.sdkClientFactory = sdkClientFactory;
        this.environmentService = environmentService;
        this.platformUtilsService = platformUtilsService;
        this.accountService = accountService;
        this.kdfConfigService = kdfConfigService;
        this.keyService = keyService;
        this.userAgent = userAgent;
        this.sdkClientOverrides = new bw_external_rxjs_namespaceObject.BehaviorSubject({});
        this.sdkClientCache = new Map();
        this.client$ = this.environmentService.environment$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)((env) => bw_default_sdk_service_awaiter(this, void 0, void 0, function* () {
            yield bw_SdkLoadService.Ready;
            const settings = this.toSettings(env);
            return yield this.sdkClientFactory.createSdkClient(settings);
        })), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        this.version$ = this.client$.pipe((0,bw_external_rxjs_namespaceObject.map)((client) => client.version()), (0,bw_external_rxjs_namespaceObject.catchError)(() => "Unsupported"));
    }
    userClient$(userId) {
        return this.sdkClientOverrides.pipe((0,bw_external_rxjs_namespaceObject.takeWhile)((clients) => clients[userId] !== bw_UnsetClient, false), (0,bw_external_rxjs_namespaceObject.map)((clients) => {
            if (clients[userId] === bw_UnsetClient) {
                throw new Error("Encountered UnsetClient even though it should have been filtered out");
            }
            return clients[userId];
        }), (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(), (0,bw_external_rxjs_namespaceObject.switchMap)((clientOverride) => {
            if (clientOverride) {
                return (0,bw_external_rxjs_namespaceObject.of)(clientOverride);
            }
            return this.internalClient$(userId);
        }), (0,bw_external_rxjs_namespaceObject.throwIfEmpty)(() => new bw_UserNotLoggedInError(userId)));
    }
    setClient(userId, client) {
        const previousValue = this.sdkClientOverrides.value[userId];
        this.sdkClientOverrides.next(Object.assign(Object.assign({}, this.sdkClientOverrides.value), { [userId]: client ? new bw_Rc(client) : bw_UnsetClient }));
        if (previousValue !== bw_UnsetClient && previousValue !== undefined) {
            previousValue.markForDisposal();
        }
    }
    /**
     * This method is used to create a client for a specific user by using the existing state of the application.
     * This methods is a fallback for when no client has been provided by Auth. As Auth starts implementing the
     * client creation, this method will be deprecated.
     * @param userId The user id for which to create the client
     * @returns An observable that emits the client for the user
     */
    internalClient$(userId) {
        const cached = this.sdkClientCache.get(userId);
        if (cached !== undefined) {
            return cached;
        }
        const account$ = this.accountService.accounts$.pipe((0,bw_external_rxjs_namespaceObject.map)((accounts) => accounts[userId]), (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)());
        const kdfParams$ = this.kdfConfigService.getKdfConfig$(userId).pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)());
        const privateKey$ = this.keyService
            .userEncryptedPrivateKey$(userId)
            .pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)());
        const userKey$ = this.keyService.userKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)());
        const orgKeys$ = this.keyService.encryptedOrgKeys$(userId).pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)(bw_compareValues));
        const client$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.environmentService.getEnvironment$(userId),
            account$,
            kdfParams$,
            privateKey$,
            userKey$,
            orgKeys$,
            bw_SdkLoadService.Ready, // Makes sure we wait (once) for the SDK to be loaded
        ]).pipe(
        // switchMap is required to allow the clean-up logic to be executed when `combineLatest` emits a new value.
        (0,bw_external_rxjs_namespaceObject.switchMap)(([env, account, kdfParams, privateKey, userKey, orgKeys]) => {
            // Create our own observable to be able to implement clean-up logic
            return new bw_external_rxjs_namespaceObject.Observable((subscriber) => {
                const createAndInitializeClient = () => bw_default_sdk_service_awaiter(this, void 0, void 0, function* () {
                    if (env == null || kdfParams == null || privateKey == null || userKey == null) {
                        return undefined;
                    }
                    const settings = this.toSettings(env);
                    const client = yield this.sdkClientFactory.createSdkClient(settings);
                    yield this.initializeClient(client, account, kdfParams, privateKey, userKey, orgKeys);
                    return client;
                });
                let client;
                createAndInitializeClient()
                    .then((c) => {
                    client = c === undefined ? undefined : new bw_Rc(c);
                    subscriber.next(client);
                })
                    .catch((e) => {
                    subscriber.error(e);
                });
                return () => client === null || client === void 0 ? void 0 : client.markForDisposal();
            });
        }), (0,bw_external_rxjs_namespaceObject.tap)({
            finalize: () => this.sdkClientCache.delete(userId),
        }), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
        this.sdkClientCache.set(userId, client$);
        return client$;
    }
    initializeClient(client, account, kdfParams, privateKey, userKey, orgKeys) {
        return bw_default_sdk_service_awaiter(this, void 0, void 0, function* () {
            yield client.crypto().initialize_user_crypto({
                email: account.email,
                method: { decryptedKey: { decrypted_user_key: userKey.keyB64 } },
                kdfParams: kdfParams.kdfType === bw_KdfType.PBKDF2_SHA256
                    ? {
                        pBKDF2: { iterations: kdfParams.iterations },
                    }
                    : {
                        argon2id: {
                            iterations: kdfParams.iterations,
                            memory: kdfParams.memory,
                            parallelism: kdfParams.parallelism,
                        },
                    },
                privateKey,
            });
            // We initialize the org crypto even if the org_keys are
            // null to make sure any existing org keys are cleared.
            yield client.crypto().initialize_org_crypto({
                organizationKeys: new Map(Object.entries(orgKeys !== null && orgKeys !== void 0 ? orgKeys : {})
                    .filter(([_, v]) => v.type === "organization")
                    .map(([k, v]) => [k, v.key])),
            });
        });
    }
    toSettings(env) {
        var _a;
        return {
            apiUrl: env.getApiUrl(),
            identityUrl: env.getIdentityUrl(),
            deviceType: this.toDevice(this.platformUtilsService.getDevice()),
            userAgent: (_a = this.userAgent) !== null && _a !== void 0 ? _a : navigator.userAgent,
        };
    }
    toDevice(device) {
        switch (device) {
            case bw_DeviceType.Android:
                return "Android";
            case bw_DeviceType.iOS:
                return "iOS";
            case bw_DeviceType.ChromeExtension:
                return "ChromeExtension";
            case bw_DeviceType.FirefoxExtension:
                return "FirefoxExtension";
            case bw_DeviceType.OperaExtension:
                return "OperaExtension";
            case bw_DeviceType.EdgeExtension:
                return "EdgeExtension";
            case bw_DeviceType.WindowsDesktop:
                return "WindowsDesktop";
            case bw_DeviceType.MacOsDesktop:
                return "MacOsDesktop";
            case bw_DeviceType.LinuxDesktop:
                return "LinuxDesktop";
            case bw_DeviceType.ChromeBrowser:
                return "ChromeBrowser";
            case bw_DeviceType.FirefoxBrowser:
                return "FirefoxBrowser";
            case bw_DeviceType.OperaBrowser:
                return "OperaBrowser";
            case bw_DeviceType.EdgeBrowser:
                return "EdgeBrowser";
            case bw_DeviceType.IEBrowser:
                return "IEBrowser";
            case bw_DeviceType.UnknownBrowser:
                return "UnknownBrowser";
            case bw_DeviceType.AndroidAmazon:
                return "AndroidAmazon";
            case bw_DeviceType.UWP:
                return "UWP";
            case bw_DeviceType.SafariBrowser:
                return "SafariBrowser";
            case bw_DeviceType.VivaldiBrowser:
                return "VivaldiBrowser";
            case bw_DeviceType.VivaldiExtension:
                return "VivaldiExtension";
            case bw_DeviceType.SafariExtension:
                return "SafariExtension";
            case bw_DeviceType.Server:
                return "Server";
            case bw_DeviceType.WindowsCLI:
                return "WindowsCLI";
            case bw_DeviceType.MacOsCLI:
                return "MacOsCLI";
            case bw_DeviceType.LinuxCLI:
                return "LinuxCLI";
            default:
                return "SDK";
        }
    }
}

;// ../../libs/common/src/platform/services/sdk/noop-sdk-client-factory.ts
/**
 * Noop SDK client factory.
 *
 * Used during SDK rollout to prevent bundling the SDK with some applications.
 */
class bw_NoopSdkClientFactory {
    createSdkClient(...args) {
        return Promise.reject(new Error("SDK not available"));
    }
}

;// ../../libs/common/src/platform/models/domain/state.ts
class bw_State {
    constructor(globals) {
        this.accounts = {};
        this.globals = globals;
    }
    // TODO, make Jsonify<State,TGlobalState,TAccount> work. It currently doesn't because Globals doesn't implement Jsonify.
    static fromJSON(obj, accountDeserializer) {
        if (obj == null) {
            return null;
        }
        return Object.assign(new bw_State(null), obj, {
            accounts: bw_State.buildAccountMapFromJSON(obj === null || obj === void 0 ? void 0 : obj.accounts, accountDeserializer),
        });
    }
    static buildAccountMapFromJSON(jsonAccounts, accountDeserializer) {
        if (!jsonAccounts) {
            return {};
        }
        const accounts = {};
        for (const userId in jsonAccounts) {
            accounts[userId] = accountDeserializer(jsonAccounts[userId]);
        }
        return accounts;
    }
}

;// ../../libs/common/src/platform/services/state.service.ts
var bw_state_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




const bw_keys = {
    state: "state",
    stateVersion: "stateVersion",
    global: "global",
    tempAccountSettings: "tempAccountSettings", // used to hold account specific settings (i.e clear clipboard) between initial migration and first account authentication
};
const bw_partialKeys = {
    userAutoKey: "_user_auto",
    userBiometricKey: "_user_biometric",
    autoKey: "_masterkey_auto",
    masterKey: "_masterkey",
};
const bw_DDG_SHARED_KEY = "DuckDuckGoSharedKey";
class bw_StateService {
    constructor(storageService, secureStorageService, memoryStorageService, logService, stateFactory, accountService, environmentService, tokenService, migrationRunner) {
        this.storageService = storageService;
        this.secureStorageService = secureStorageService;
        this.memoryStorageService = memoryStorageService;
        this.logService = logService;
        this.stateFactory = stateFactory;
        this.accountService = accountService;
        this.environmentService = environmentService;
        this.tokenService = tokenService;
        this.migrationRunner = migrationRunner;
        this.hasBeenInited = false;
        this.isRecoveredSession = false;
        // default account serializer, must be overridden by child class
        this.accountDeserializer = bw_Account.fromJSON;
    }
    init() {
        return bw_state_service_awaiter(this, arguments, void 0, function* (initOptions = {}) {
            // Deconstruct and apply defaults
            const { runMigrations = true } = initOptions;
            if (this.hasBeenInited) {
                return;
            }
            if (runMigrations) {
                yield this.migrationRunner.run();
            }
            else {
                // It may have been requested to not run the migrations but we should defensively not
                // continue this method until migrations have a chance to be completed elsewhere.
                yield this.migrationRunner.waitForCompletion();
            }
            yield this.state().then((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                if (state == null) {
                    yield this.setState(new bw_State(this.createGlobals()));
                }
                else {
                    this.isRecoveredSession = true;
                }
            }));
            yield this.initAccountState();
            this.hasBeenInited = true;
        });
    }
    initAccountState() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            if (this.isRecoveredSession) {
                return;
            }
            // Get all likely authenticated accounts
            const authenticatedAccounts = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.accounts$.pipe((0,bw_external_rxjs_namespaceObject.map)((accounts) => Object.keys(accounts))));
            yield this.updateState((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                for (const i in authenticatedAccounts) {
                    state = yield this.syncAccountFromDisk(authenticatedAccounts[i]);
                }
                return state;
            }));
        });
    }
    syncAccountFromDisk(userId) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                return;
            }
            const diskAccount = yield this.getAccountFromDisk({ userId: userId });
            const state = yield this.updateState((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                if (state.accounts == null) {
                    state.accounts = {};
                }
                state.accounts[userId] = this.createAccount();
                if (diskAccount == null) {
                    // Return early because we can't set the diskAccount.profile
                    // if diskAccount itself is null
                    return state;
                }
                state.accounts[userId].profile = diskAccount.profile;
                return state;
            }));
            return state;
        });
    }
    addAccount(account) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.updateState((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                state.accounts[account.profile.userId] = account;
                return state;
            }));
            yield this.scaffoldNewAccountStorage(account);
        });
    }
    clean(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(options, yield this.defaultInMemoryOptions());
            yield this.deAuthenticateAccount(options.userId);
            yield this.removeAccountFromDisk(options === null || options === void 0 ? void 0 : options.userId);
            yield this.removeAccountFromMemory(options === null || options === void 0 ? void 0 : options.userId);
        });
    }
    /**
     * user key when using the "never" option of vault timeout
     */
    getUserKeyAutoUnlock(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(this.reconcileOptions(options, { keySuffix: "auto" }), yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return null;
            }
            return yield this.secureStorageService.get(`${options.userId}${bw_partialKeys.userAutoKey}`, options);
        });
    }
    /**
     * user key when using the "never" option of vault timeout
     */
    setUserKeyAutoUnlock(value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(this.reconcileOptions(options, { keySuffix: "auto" }), yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return;
            }
            yield this.saveSecureStorageKey(bw_partialKeys.userAutoKey, value, options);
        });
    }
    /**
     * User's encrypted symmetric key when using biometrics
     */
    getUserKeyBiometric(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(this.reconcileOptions(options, { keySuffix: "biometric" }), yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return null;
            }
            return yield this.secureStorageService.get(`${options.userId}${bw_partialKeys.userBiometricKey}`, options);
        });
    }
    hasUserKeyBiometric(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(this.reconcileOptions(options, { keySuffix: "biometric" }), yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return false;
            }
            return yield this.secureStorageService.has(`${options.userId}${bw_partialKeys.userBiometricKey}`, options);
        });
    }
    setUserKeyBiometric(value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(this.reconcileOptions(options, { keySuffix: "biometric" }), yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return;
            }
            yield this.saveSecureStorageKey(bw_partialKeys.userBiometricKey, value, options);
        });
    }
    /**
     * @deprecated Use UserKeyAuto instead
     */
    setCryptoMasterKeyAuto(value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(this.reconcileOptions(options, { keySuffix: "auto" }), yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return;
            }
            yield this.saveSecureStorageKey(bw_partialKeys.autoKey, value, options);
        });
    }
    /**
     * @deprecated I don't see where this is even used
     */
    getCryptoMasterKeyB64(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(options, yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return null;
            }
            return yield this.secureStorageService.get(`${options === null || options === void 0 ? void 0 : options.userId}${bw_partialKeys.masterKey}`, options);
        });
    }
    /**
     * @deprecated I don't see where this is even used
     */
    setCryptoMasterKeyB64(value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(options, yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return;
            }
            yield this.saveSecureStorageKey(bw_partialKeys.masterKey, value, options);
        });
    }
    getDuckDuckGoSharedKey(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(options, yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return null;
            }
            return yield this.secureStorageService.get(bw_DDG_SHARED_KEY, options);
        });
    }
    setDuckDuckGoSharedKey(value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            options = this.reconcileOptions(options, yield this.defaultSecureStorageOptions());
            if ((options === null || options === void 0 ? void 0 : options.userId) == null) {
                return;
            }
            value == null
                ? yield this.secureStorageService.remove(bw_DDG_SHARED_KEY, options)
                : yield this.secureStorageService.save(bw_DDG_SHARED_KEY, value, options);
        });
    }
    setEnableDuckDuckGoBrowserIntegration(value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const globals = yield this.getGlobals(this.reconcileOptions(options, yield this.defaultOnDiskOptions()));
            globals.enableDuckDuckGoBrowserIntegration = value;
            yield this.saveGlobals(globals, this.reconcileOptions(options, yield this.defaultOnDiskOptions()));
        });
    }
    /**
     * @deprecated Use UserKey instead
     */
    getEncryptedCryptoSymmetricKey(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            return (_a = (yield this.getAccount(this.reconcileOptions(options, yield this.defaultOnDiskOptions())))) === null || _a === void 0 ? void 0 : _a.keys.cryptoSymmetricKey.encrypted;
        });
    }
    getIsAuthenticated(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return ((yield this.tokenService.getAccessToken(options === null || options === void 0 ? void 0 : options.userId)) != null &&
                (yield this.getUserId(options)) != null);
        });
    }
    getUserId(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            return (_b = (_a = (yield this.getAccount(this.reconcileOptions(options, yield this.defaultOnDiskOptions())))) === null || _a === void 0 ? void 0 : _a.profile) === null || _b === void 0 ? void 0 : _b.userId;
        });
    }
    getGlobals(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            let globals;
            if (this.useMemory(options.storageLocation)) {
                globals = yield this.getGlobalsFromMemory();
            }
            if (this.useDisk && globals == null) {
                globals = yield this.getGlobalsFromDisk(options);
            }
            if (globals == null) {
                globals = this.createGlobals();
            }
            return globals;
        });
    }
    saveGlobals(globals, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return this.useMemory(options.storageLocation)
                ? this.saveGlobalsToMemory(globals)
                : yield this.saveGlobalsToDisk(globals, options);
        });
    }
    getGlobalsFromMemory() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.state()).globals;
        });
    }
    getGlobalsFromDisk(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return yield this.storageService.get(bw_keys.global, options);
        });
    }
    saveGlobalsToMemory(globals) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.updateState((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                state.globals = globals;
                return state;
            }));
        });
    }
    saveGlobalsToDisk(globals, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            if (options.useSecureStorage) {
                yield this.secureStorageService.save(bw_keys.global, globals, options);
            }
            else {
                yield this.storageService.save(bw_keys.global, globals, options);
            }
        });
    }
    getAccount(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            try {
                let account;
                if (this.useMemory(options.storageLocation)) {
                    account = yield this.getAccountFromMemory(options);
                }
                if (this.useDisk(options.storageLocation) && account == null) {
                    account = yield this.getAccountFromDisk(options);
                }
                return account;
            }
            catch (e) {
                this.logService.error(e);
            }
        });
    }
    getAccountFromMemory(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const userId = (_a = options.userId) !== null && _a !== void 0 ? _a : (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id))));
            return yield this.state().then((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                if (state.accounts == null) {
                    return null;
                }
                return state.accounts[userId];
            }));
        });
    }
    getAccountFromDisk(options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            var _a, _b;
            const userId = (_a = options.userId) !== null && _a !== void 0 ? _a : (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id))));
            if (userId == null) {
                return null;
            }
            const account = (options === null || options === void 0 ? void 0 : options.useSecureStorage)
                ? ((_b = (yield this.secureStorageService.get(options.userId, options))) !== null && _b !== void 0 ? _b : (yield this.storageService.get(options.userId, this.reconcileOptions(options, { htmlStorageLocation: bw_HtmlStorageLocation.Local }))))
                : yield this.storageService.get(options.userId, options);
            return account;
        });
    }
    useMemory(storageLocation) {
        return storageLocation === bw_StorageLocation.Memory || storageLocation === bw_StorageLocation.Both;
    }
    useDisk(storageLocation) {
        return storageLocation === bw_StorageLocation.Disk || storageLocation === bw_StorageLocation.Both;
    }
    saveAccount(account_1) {
        return bw_state_service_awaiter(this, arguments, void 0, function* (account, options = {
            storageLocation: bw_StorageLocation.Both,
            useSecureStorage: false,
        }) {
            return this.useMemory(options.storageLocation)
                ? yield this.saveAccountToMemory(account)
                : yield this.saveAccountToDisk(account, options);
        });
    }
    saveAccountToDisk(account, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const storageLocation = options.useSecureStorage
                ? this.secureStorageService
                : this.storageService;
            yield storageLocation.save(`${options.userId}`, account, options);
        });
    }
    saveAccountToMemory(account) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            if ((yield this.getAccountFromMemory({ userId: account.profile.userId })) !== null) {
                yield this.updateState((state) => {
                    return new Promise((resolve) => {
                        state.accounts[account.profile.userId] = account;
                        resolve(state);
                    });
                });
            }
        });
    }
    scaffoldNewAccountStorage(account) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            // We don't want to manipulate the referenced in memory account
            const deepClone = JSON.parse(JSON.stringify(account));
            yield this.scaffoldNewAccountLocalStorage(deepClone);
            yield this.scaffoldNewAccountSessionStorage(deepClone);
            yield this.scaffoldNewAccountMemoryStorage(deepClone);
        });
    }
    // TODO: There is a tech debt item for splitting up these methods - only Web uses multiple storage locations in its storageService.
    // For now these methods exist with some redundancy to facilitate this special web requirement.
    scaffoldNewAccountLocalStorage(account) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.saveAccount(account, this.reconcileOptions({ userId: account.profile.userId }, yield this.defaultOnDiskLocalOptions()));
        });
    }
    scaffoldNewAccountMemoryStorage(account) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.storageService.save(account.profile.userId, account, yield this.defaultOnDiskMemoryOptions());
            yield this.saveAccount(account, this.reconcileOptions({ userId: account.profile.userId }, yield this.defaultOnDiskMemoryOptions()));
        });
    }
    scaffoldNewAccountSessionStorage(account) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.storageService.save(account.profile.userId, account, yield this.defaultOnDiskMemoryOptions());
            yield this.saveAccount(account, this.reconcileOptions({ userId: account.profile.userId }, yield this.defaultOnDiskOptions()));
        });
    }
    reconcileOptions(requestedOptions, defaultOptions) {
        var _a, _b, _c, _d, _e;
        if (requestedOptions == null) {
            return defaultOptions;
        }
        requestedOptions.userId = (_a = requestedOptions === null || requestedOptions === void 0 ? void 0 : requestedOptions.userId) !== null && _a !== void 0 ? _a : defaultOptions.userId;
        requestedOptions.storageLocation =
            (_b = requestedOptions === null || requestedOptions === void 0 ? void 0 : requestedOptions.storageLocation) !== null && _b !== void 0 ? _b : defaultOptions.storageLocation;
        requestedOptions.useSecureStorage =
            (_c = requestedOptions === null || requestedOptions === void 0 ? void 0 : requestedOptions.useSecureStorage) !== null && _c !== void 0 ? _c : defaultOptions.useSecureStorage;
        requestedOptions.htmlStorageLocation =
            (_d = requestedOptions === null || requestedOptions === void 0 ? void 0 : requestedOptions.htmlStorageLocation) !== null && _d !== void 0 ? _d : defaultOptions.htmlStorageLocation;
        requestedOptions.keySuffix = (_e = requestedOptions === null || requestedOptions === void 0 ? void 0 : requestedOptions.keySuffix) !== null && _e !== void 0 ? _e : defaultOptions.keySuffix;
        return requestedOptions;
    }
    defaultInMemoryOptions() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id)));
            return {
                storageLocation: bw_StorageLocation.Memory,
                userId,
            };
        });
    }
    defaultOnDiskOptions() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id)));
            return {
                storageLocation: bw_StorageLocation.Disk,
                htmlStorageLocation: bw_HtmlStorageLocation.Session,
                userId,
                useSecureStorage: false,
            };
        });
    }
    defaultOnDiskLocalOptions() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id)));
            return {
                storageLocation: bw_StorageLocation.Disk,
                htmlStorageLocation: bw_HtmlStorageLocation.Local,
                userId,
                useSecureStorage: false,
            };
        });
    }
    defaultOnDiskMemoryOptions() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id)));
            return {
                storageLocation: bw_StorageLocation.Disk,
                htmlStorageLocation: bw_HtmlStorageLocation.Memory,
                userId,
                useSecureStorage: false,
            };
        });
    }
    defaultSecureStorageOptions() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id)));
            return {
                storageLocation: bw_StorageLocation.Disk,
                useSecureStorage: true,
                userId,
            };
        });
    }
    getActiveUserIdFromStorage() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
        });
    }
    removeAccountFromLocalStorage() {
        return bw_state_service_awaiter(this, arguments, void 0, function* (userId = null) {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id))));
            const storedAccount = yield this.getAccount(this.reconcileOptions({ userId: userId }, yield this.defaultOnDiskLocalOptions()));
            yield this.saveAccount(this.resetAccount(storedAccount), this.reconcileOptions({ userId: userId }, yield this.defaultOnDiskLocalOptions()));
        });
    }
    removeAccountFromSessionStorage() {
        return bw_state_service_awaiter(this, arguments, void 0, function* (userId = null) {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id))));
            const storedAccount = yield this.getAccount(this.reconcileOptions({ userId: userId }, yield this.defaultOnDiskOptions()));
            yield this.saveAccount(this.resetAccount(storedAccount), this.reconcileOptions({ userId: userId }, yield this.defaultOnDiskOptions()));
        });
    }
    removeAccountFromSecureStorage() {
        return bw_state_service_awaiter(this, arguments, void 0, function* (userId = null) {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id))));
            yield this.setUserKeyAutoUnlock(null, { userId: userId });
            yield this.setUserKeyBiometric(null, { userId: userId });
            yield this.setCryptoMasterKeyAuto(null, { userId: userId });
            yield this.setCryptoMasterKeyB64(null, { userId: userId });
        });
    }
    removeAccountFromMemory() {
        return bw_state_service_awaiter(this, arguments, void 0, function* (userId = null) {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id))));
            yield this.updateState((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                delete state.accounts[userId];
                return state;
            }));
        });
    }
    // settings persist even on reset, and are not affected by this method
    resetAccount(account) {
        // All settings have been moved to StateProviders
        return this.createAccount();
    }
    createAccount(init = null) {
        return this.stateFactory.createAccount(init);
    }
    createGlobals(init = null) {
        return this.stateFactory.createGlobal(init);
    }
    deAuthenticateAccount(userId) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            // We must have a manual call to clear tokens as we can't leverage state provider to clean
            // up our data as we have secure storage in the mix.
            yield this.tokenService.clearTokens(userId);
        });
    }
    removeAccountFromDisk(userId) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.removeAccountFromSessionStorage(userId);
            yield this.removeAccountFromLocalStorage(userId);
            yield this.removeAccountFromSecureStorage(userId);
        });
    }
    saveSecureStorageKey(key, value, options) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return value == null
                ? yield this.secureStorageService.remove(`${options.userId}${key}`, options)
                : yield this.secureStorageService.save(`${options.userId}${key}`, value, options);
        });
    }
    state() {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            let state = yield this.memoryStorageService.get(bw_keys.state);
            if (this.memoryStorageService.valuesRequireDeserialization) {
                state = bw_State.fromJSON(state, this.accountDeserializer);
            }
            return state;
        });
    }
    setState(state) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            yield this.memoryStorageService.save(bw_keys.state, state);
            return state;
        });
    }
    updateState(stateUpdater) {
        return bw_state_service_awaiter(this, void 0, void 0, function* () {
            return yield this.state().then((state) => bw_state_service_awaiter(this, void 0, void 0, function* () {
                const updatedState = yield stateUpdater(state);
                if (updatedState == null) {
                    throw new Error("Attempted to update state to null value");
                }
                return yield this.setState(updatedState);
            }));
        });
    }
}

;// ../../libs/common/src/platform/services/storage-service.provider.ts
/**
 * A provider for getting client specific computed storage locations and services.
 */
class bw_StorageServiceProvider {
    constructor(diskStorageService, memoryStorageService) {
        this.diskStorageService = diskStorageService;
        this.memoryStorageService = memoryStorageService;
    }
    /**
     * Computes the location and corresponding service for a given client.
     *
     * **NOTE** The default implementation does not respect client overrides and if clients
     * have special overrides they are responsible for implementing this service.
     * @param defaultLocation The default location to use if no client specific override is preferred.
     * @param overrides Client specific overrides
     * @returns The computed storage location and corresponding storage service to use to get/store state.
     * @throws If there is no configured storage service for the given inputs.
     */
    get(defaultLocation, overrides) {
        switch (defaultLocation) {
            case "disk":
                return [defaultLocation, this.diskStorageService];
            case "memory":
                return [defaultLocation, this.memoryStorageService];
            default:
                throw new Error(`Unexpected location: ${defaultLocation}`);
        }
    }
}

;// ../../libs/common/src/platform/services/user-auto-unlock-key.service.ts
var bw_user_auto_unlock_key_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

// TODO: this is a half measure improvement which allows us to reduce some side effects today (keyService.getUserKey setting user key in memory if auto key exists)
// but ideally, in the future, we would be able to put this logic into the keyService
// after the vault timeout settings service is transitioned to state provider so that
// the getUserKey logic can simply go to the correct location based on the vault timeout settings
// similar to the TokenService (it would either go to secure storage for the auto user key or memory for the user key)
class bw_UserAutoUnlockKeyService {
    constructor(keyService) {
        this.keyService = keyService;
    }
    /**
     * The presence of the user key in memory dictates whether the user's vault is locked or unlocked.
     * However, for users that have the auto unlock user key set, we need to set the user key in memory
     * on application bootstrap and on active account changes so that the user's vault loads unlocked.
     * @param userId - The user id to check for an auto user key.
     * @returns True if the auto user key is set successfully, false otherwise.
     */
    setUserKeyInMemoryIfAutoUserKeySet(userId) {
        return bw_user_auto_unlock_key_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                return false;
            }
            const autoUserKey = yield this.keyService.getUserKeyFromStorage(bw_KeySuffixOptions.Auto, userId);
            if (autoUserKey == null) {
                return false;
            }
            yield this.keyService.setUserKey(autoUserKey, userId);
            return true;
        });
    }
}

;// ../../libs/common/src/platform/state/user-state.ts
const bw_activeMarker = Symbol("active");

;// ../../libs/common/src/platform/state/implementations/default-active-user-state.ts
var bw_default_active_user_state_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_DefaultActiveUserState {
    constructor(keyDefinition, activeUserId$, singleUserStateProvider) {
        this.keyDefinition = keyDefinition;
        this.activeUserId$ = activeUserId$;
        this.singleUserStateProvider = singleUserStateProvider;
        this.combinedState$ = this.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((userId) => userId != null
            ? this.singleUserStateProvider.get(userId, this.keyDefinition).combinedState$
            : bw_external_rxjs_namespaceObject.NEVER));
        // State should just be combined state without the user id
        this.state$ = this.combinedState$.pipe((0,bw_external_rxjs_namespaceObject.map)(([_userId, state]) => state));
    }
    update(configureState_1) {
        return bw_default_active_user_state_awaiter(this, arguments, void 0, function* (configureState, options = {}) {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.timeout)({
                first: 1000,
                with: () => (0,bw_external_rxjs_namespaceObject.throwError)(() => new Error(`Timeout while retrieving active user for key ${this.keyDefinition.fullName}.`)),
            })));
            if (userId == null) {
                throw new Error(`Error storing ${this.keyDefinition.fullName} for the active user: No active user at this time.`);
            }
            return [
                userId,
                yield this.singleUserStateProvider
                    .get(userId, this.keyDefinition)
                    .update(configureState, options),
            ];
        });
    }
}

;// ../../libs/common/src/platform/state/implementations/default-active-user-state.provider.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_DefaultActiveUserStateProvider {
    constructor(accountService, singleUserStateProvider) {
        this.accountService = accountService;
        this.singleUserStateProvider = singleUserStateProvider;
        this.activeUserId$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((account) => account === null || account === void 0 ? void 0 : account.id), 
        // To avoid going to storage when we don't need to, only get updates when there is a true change.
        (0,bw_external_rxjs_namespaceObject.distinctUntilChanged)((a, b) => (a == null || b == null ? a == b : a === b)));
    }
    get(keyDefinition) {
        // All other providers cache the creation of their corresponding `State` objects, this instance
        // doesn't need to do that since it calls `SingleUserStateProvider` it will go through their caching
        // layer, because of that, the creation of this instance is quite simple and not worth caching.
        return new bw_DefaultActiveUserState(keyDefinition, this.activeUserId$, this.singleUserStateProvider);
    }
}

;// ../../libs/common/src/platform/state/implementations/default-derived-state.ts
var bw_default_derived_state_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

/**
 * Default derived state
 */
class bw_DefaultDerivedState {
    constructor(parentState$, deriveDefinition, dependencies) {
        this.parentState$ = parentState$;
        this.deriveDefinition = deriveDefinition;
        this.dependencies = dependencies;
        this.forcedValueSubject = new bw_external_rxjs_namespaceObject.Subject();
        this.storageKey = deriveDefinition.storageKey;
        const derivedState$ = this.parentState$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)((state) => bw_default_derived_state_awaiter(this, void 0, void 0, function* () {
            let derivedStateOrPromise = this.deriveDefinition.derive(state, this.dependencies);
            if (derivedStateOrPromise instanceof Promise) {
                derivedStateOrPromise = yield derivedStateOrPromise;
            }
            const derivedState = derivedStateOrPromise;
            return derivedState;
        })));
        this.state$ = (0,bw_external_rxjs_namespaceObject.merge)(this.forcedValueSubject, derivedState$).pipe((0,bw_external_rxjs_namespaceObject.share)({
            connector: () => {
                return new bw_external_rxjs_namespaceObject.ReplaySubject(1);
            },
            resetOnRefCountZero: () => (0,bw_external_rxjs_namespaceObject.timer)(this.deriveDefinition.cleanupDelayMs),
        }));
    }
    forceValue(value) {
        return bw_default_derived_state_awaiter(this, void 0, void 0, function* () {
            this.forcedValueSubject.next(value);
            return value;
        });
    }
}

;// ../../libs/common/src/platform/state/implementations/default-derived-state.provider.ts

class bw_DefaultDerivedStateProvider {
    constructor() {
        /**
         * The cache uses a WeakMap to maintain separate derived states per user.
         * Each user's state Observable acts as a unique key, without needing to
         * pass around `userId`. Also, when a user's state Observable is cleaned up
         * (like during an account swap) their cache is automatically garbage
         * collected.
         */
        this.cache = new WeakMap();
    }
    get(parentState$, deriveDefinition, dependencies) {
        let stateCache = this.cache.get(parentState$);
        if (!stateCache) {
            stateCache = {};
            this.cache.set(parentState$, stateCache);
        }
        const cacheKey = deriveDefinition.buildCacheKey();
        const existingDerivedState = stateCache[cacheKey];
        if (existingDerivedState != null) {
            // I have to cast out of the unknown generic but this should be safe if rules
            // around domain token are made
            return existingDerivedState;
        }
        const newDerivedState = this.buildDerivedState(parentState$, deriveDefinition, dependencies);
        stateCache[cacheKey] = newDerivedState;
        return newDerivedState;
    }
    buildDerivedState(parentState$, deriveDefinition, dependencies) {
        return new bw_DefaultDerivedState(parentState$, deriveDefinition, dependencies);
    }
}

;// ../../libs/common/src/platform/state/state-update-options.ts
const bw_DEFAULT_OPTIONS = {
    shouldUpdate: () => true,
    combineLatestWith: null,
    msTimeout: 1000,
};
function bw_populateOptionsWithDefault(options) {
    return Object.assign(Object.assign({}, bw_DEFAULT_OPTIONS), options);
}

;// ../../libs/common/src/platform/state/implementations/util.ts
var bw_util_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
function bw_getStoredValue(key, storage, deserializer) {
    return bw_util_awaiter(this, void 0, void 0, function* () {
        if (storage.valuesRequireDeserialization) {
            const jsonValue = yield storage.get(key);
            return deserializer(jsonValue);
        }
        else {
            const value = yield storage.get(key);
            return value !== null && value !== void 0 ? value : null;
        }
    });
}

;// ../../libs/common/src/platform/state/implementations/state-base.ts
var bw_state_base_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_StateBase {
    constructor(key, storageService, keyDefinition, logService) {
        this.key = key;
        this.storageService = storageService;
        this.keyDefinition = keyDefinition;
        this.logService = logService;
        const storageUpdate$ = storageService.updates$.pipe((0,bw_external_rxjs_namespaceObject.filter)((storageUpdate) => storageUpdate.key === key), (0,bw_external_rxjs_namespaceObject.switchMap)((storageUpdate) => bw_state_base_awaiter(this, void 0, void 0, function* () {
            if (storageUpdate.updateType === "remove") {
                return null;
            }
            return yield bw_getStoredValue(key, storageService, keyDefinition.deserializer);
        })));
        let state$ = (0,bw_external_rxjs_namespaceObject.merge)((0,bw_external_rxjs_namespaceObject.defer)(() => bw_getStoredValue(key, storageService, keyDefinition.deserializer)), storageUpdate$);
        if (keyDefinition.debug.enableRetrievalLogging) {
            state$ = state$.pipe((0,bw_external_rxjs_namespaceObject.tap)({
                next: (v) => {
                    this.logService.info(`Retrieving '${key}' from storage, value is ${v == null ? "null" : "non-null"}`);
                },
            }));
        }
        // If 0 cleanup is chosen, treat this as absolutely no cache
        if (keyDefinition.cleanupDelayMs !== 0) {
            state$ = state$.pipe((0,bw_external_rxjs_namespaceObject.share)({
                connector: () => new bw_external_rxjs_namespaceObject.ReplaySubject(1),
                resetOnRefCountZero: () => (0,bw_external_rxjs_namespaceObject.timer)(keyDefinition.cleanupDelayMs),
            }));
        }
        this.state$ = state$;
    }
    update(configureState_1) {
        return bw_state_base_awaiter(this, arguments, void 0, function* (configureState, options = {}) {
            options = bw_populateOptionsWithDefault(options);
            if (this.updatePromise != null) {
                yield this.updatePromise;
            }
            try {
                this.updatePromise = this.internalUpdate(configureState, options);
                return yield this.updatePromise;
            }
            finally {
                this.updatePromise = null;
            }
        });
    }
    internalUpdate(configureState, options) {
        return bw_state_base_awaiter(this, void 0, void 0, function* () {
            const currentState = yield this.getStateForUpdate();
            const combinedDependencies = options.combineLatestWith != null
                ? yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(options.combineLatestWith.pipe((0,bw_external_rxjs_namespaceObject.timeout)(options.msTimeout)))
                : null;
            if (!options.shouldUpdate(currentState, combinedDependencies)) {
                return currentState;
            }
            const newState = configureState(currentState, combinedDependencies);
            yield this.doStorageSave(newState, currentState);
            return newState;
        });
    }
    doStorageSave(newState, oldState) {
        return bw_state_base_awaiter(this, void 0, void 0, function* () {
            if (this.keyDefinition.debug.enableUpdateLogging) {
                this.logService.info(`Updating '${this.key}' from ${oldState == null ? "null" : "non-null"} to ${newState == null ? "null" : "non-null"}`);
            }
            yield this.storageService.save(this.key, newState);
        });
    }
    /** For use in update methods, does not wait for update to complete before yielding state.
     * The expectation is that that await is already done
     */
    getStateForUpdate() {
        return bw_state_base_awaiter(this, void 0, void 0, function* () {
            return yield bw_getStoredValue(this.key, this.storageService, this.keyDefinition.deserializer);
        });
    }
}

;// ../../libs/common/src/platform/state/implementations/default-global-state.ts


class bw_DefaultGlobalState extends bw_StateBase {
    constructor(keyDefinition, chosenLocation, logService) {
        super(bw_globalKeyBuilder(keyDefinition), chosenLocation, keyDefinition, logService);
    }
}

;// ../../libs/common/src/platform/state/implementations/default-global-state.provider.ts

class bw_DefaultGlobalStateProvider {
    constructor(storageServiceProvider, logService) {
        this.storageServiceProvider = storageServiceProvider;
        this.logService = logService;
        this.globalStateCache = {};
    }
    get(keyDefinition) {
        const [location, storageService] = this.storageServiceProvider.get(keyDefinition.stateDefinition.defaultStorageLocation, keyDefinition.stateDefinition.storageLocationOverrides);
        const cacheKey = this.buildCacheKey(location, keyDefinition);
        const existingGlobalState = this.globalStateCache[cacheKey];
        if (existingGlobalState != null) {
            // The cast into the actual generic is safe because of rules around key definitions
            // being unique.
            return existingGlobalState;
        }
        const newGlobalState = new bw_DefaultGlobalState(keyDefinition, storageService, this.logService);
        this.globalStateCache[cacheKey] = newGlobalState;
        return newGlobalState;
    }
    buildCacheKey(location, keyDefinition) {
        return `${location}_${keyDefinition.fullName}`;
    }
}

;// ../../libs/common/src/platform/state/implementations/default-single-user-state.ts
var bw_default_single_user_state_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_DefaultSingleUserState extends bw_StateBase {
    constructor(userId, keyDefinition, chosenLocation, stateEventRegistrarService, logService) {
        super(keyDefinition.buildKey(userId), chosenLocation, keyDefinition, logService);
        this.userId = userId;
        this.stateEventRegistrarService = stateEventRegistrarService;
        this.combinedState$ = (0,bw_external_rxjs_namespaceObject.combineLatest)([(0,bw_external_rxjs_namespaceObject.of)(userId), this.state$]);
    }
    doStorageSave(newState, oldState) {
        const _super = Object.create(null, {
            doStorageSave: { get: () => super.doStorageSave }
        });
        return bw_default_single_user_state_awaiter(this, void 0, void 0, function* () {
            yield _super.doStorageSave.call(this, newState, oldState);
            if (newState != null && oldState == null) {
                yield this.stateEventRegistrarService.registerEvents(this.keyDefinition);
            }
        });
    }
}

;// ../../libs/common/src/platform/state/implementations/default-single-user-state.provider.ts

class bw_DefaultSingleUserStateProvider {
    constructor(storageServiceProvider, stateEventRegistrarService, logService) {
        this.storageServiceProvider = storageServiceProvider;
        this.stateEventRegistrarService = stateEventRegistrarService;
        this.logService = logService;
        this.cache = {};
    }
    get(userId, keyDefinition) {
        const [location, storageService] = this.storageServiceProvider.get(keyDefinition.stateDefinition.defaultStorageLocation, keyDefinition.stateDefinition.storageLocationOverrides);
        const cacheKey = this.buildCacheKey(location, userId, keyDefinition);
        const existingUserState = this.cache[cacheKey];
        if (existingUserState != null) {
            // I have to cast out of the unknown generic but this should be safe if rules
            // around domain token are made
            return existingUserState;
        }
        const newUserState = new bw_DefaultSingleUserState(userId, keyDefinition, storageService, this.stateEventRegistrarService, this.logService);
        this.cache[cacheKey] = newUserState;
        return newUserState;
    }
    buildCacheKey(location, userId, keyDefinition) {
        return `${location}_${keyDefinition.fullName}_${userId}`;
    }
}

;// ../../libs/common/src/platform/state/implementations/default-state.provider.ts
var bw_default_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_DefaultStateProvider {
    constructor(activeUserStateProvider, singleUserStateProvider, globalStateProvider, derivedStateProvider) {
        this.activeUserStateProvider = activeUserStateProvider;
        this.singleUserStateProvider = singleUserStateProvider;
        this.globalStateProvider = globalStateProvider;
        this.derivedStateProvider = derivedStateProvider;
        this.getActive = this.activeUserStateProvider.get.bind(this.activeUserStateProvider);
        this.getUser = this.singleUserStateProvider.get.bind(this.singleUserStateProvider);
        this.getGlobal = this.globalStateProvider.get.bind(this.globalStateProvider);
        this.getDerived = this.derivedStateProvider.get.bind(this.derivedStateProvider);
        this.activeUserId$ = this.activeUserStateProvider.activeUserId$;
    }
    getUserState$(userKeyDefinition, userId) {
        if (userId) {
            return this.getUser(userId, userKeyDefinition).state$;
        }
        else {
            return this.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.filter)((userId) => userId != null), // Filter out null-ish user ids since we can't get state for a null user id
            (0,bw_external_rxjs_namespaceObject.take)(1), (0,bw_external_rxjs_namespaceObject.switchMap)((userId) => this.getUser(userId, userKeyDefinition).state$));
        }
    }
    getUserStateOrDefault$(userKeyDefinition, config) {
        const { userId, defaultValue = null } = config;
        if (userId) {
            return this.getUser(userId, userKeyDefinition).state$;
        }
        else {
            return this.activeUserId$.pipe((0,bw_external_rxjs_namespaceObject.take)(1), (0,bw_external_rxjs_namespaceObject.switchMap)((userId) => userId != null ? this.getUser(userId, userKeyDefinition).state$ : (0,bw_external_rxjs_namespaceObject.of)(defaultValue)));
        }
    }
    setUserState(userKeyDefinition, value, userId) {
        return bw_default_state_provider_awaiter(this, void 0, void 0, function* () {
            if (userId) {
                return [userId, yield this.getUser(userId, userKeyDefinition).update(() => value)];
            }
            else {
                return yield this.getActive(userKeyDefinition).update(() => value);
            }
        });
    }
}

;// ../../libs/common/src/platform/state/storage/memory-storage.service.ts
var bw_storage_memory_storage_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_memory_storage_service_MemoryStorageService extends bw_AbstractStorageService {
    constructor() {
        super(...arguments);
        this.store = {};
        this.updatesSubject = new bw_external_rxjs_namespaceObject.Subject();
    }
    get valuesRequireDeserialization() {
        return true;
    }
    get updates$() {
        return this.updatesSubject.asObservable();
    }
    get(key) {
        const json = this.store[key];
        if (json) {
            const obj = JSON.parse(json);
            return Promise.resolve(obj);
        }
        return Promise.resolve(null);
    }
    has(key) {
        return bw_storage_memory_storage_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.get(key)) != null;
        });
    }
    save(key, obj) {
        if (obj == null) {
            return this.remove(key);
        }
        // TODO: Remove once foreground/background contexts are separated in browser
        // Needed to ensure ownership of all memory by the context running the storage service
        this.store[key] = JSON.stringify(obj);
        this.updatesSubject.next({ key, updateType: "save" });
        return Promise.resolve();
    }
    remove(key) {
        delete this.store[key];
        this.updatesSubject.next({ key, updateType: "remove" });
        return Promise.resolve();
    }
}

;// ../../libs/common/src/admin-console/models/data/provider.data.ts
class bw_ProviderData {
    constructor(response) {
        this.id = response.id;
        this.name = response.name;
        this.status = response.status;
        this.type = response.type;
        this.enabled = response.enabled;
        this.userId = response.userId;
        this.useEvents = response.useEvents;
        this.providerStatus = response.providerStatus;
    }
}

;// ../../libs/common/src/tools/send/models/data/send-file.data.ts
class bw_SendFileData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.id = data.id;
        this.fileName = data.fileName;
        this.size = data.size;
        this.sizeName = data.sizeName;
    }
}

;// ../../libs/common/src/tools/send/models/data/send-text.data.ts
class bw_SendTextData {
    constructor(data) {
        if (data == null) {
            return;
        }
        this.text = data.text;
        this.hidden = data.hidden;
    }
}

;// ../../libs/common/src/tools/send/models/data/send.data.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_SendData {
    constructor(response) {
        if (response == null) {
            return;
        }
        this.id = response.id;
        this.accessId = response.accessId;
        this.type = response.type;
        this.name = response.name;
        this.notes = response.notes;
        this.key = response.key;
        this.maxAccessCount = response.maxAccessCount;
        this.accessCount = response.accessCount;
        this.revisionDate = response.revisionDate;
        this.expirationDate = response.expirationDate;
        this.deletionDate = response.deletionDate;
        this.password = response.password;
        this.disabled = response.disable;
        this.hideEmail = response.hideEmail;
        switch (this.type) {
            case bw_SendType.Text:
                this.text = new bw_SendTextData(response.text);
                break;
            case bw_SendType.File:
                this.file = new bw_SendFileData(response.file);
                break;
            default:
                break;
        }
    }
}

;// ../../libs/common/src/vault/models/data/folder.data.ts
class bw_FolderData {
    constructor(response) {
        this.name = response === null || response === void 0 ? void 0 : response.name;
        this.id = response === null || response === void 0 ? void 0 : response.id;
        this.revisionDate = response === null || response === void 0 ? void 0 : response.revisionDate;
    }
    static fromJSON(obj) {
        return Object.assign(new bw_FolderData({}), obj);
    }
}

;// ../../libs/common/src/platform/misc/sequentialize.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
const bw_caches = new Map();
const bw_getCache = (obj) => {
    let cache = bw_caches.get(obj);
    if (cache != null) {
        return cache;
    }
    cache = new Map();
    bw_caches.set(obj, cache);
    return cache;
};
function bw_clearCaches() {
    bw_caches.clear();
}
/**
 * Use as a Decorator on async functions, it will prevent multiple 'active' calls as the same time
 *
 * If a promise was returned from a previous call to this function, that hasn't yet resolved it will
 * be returned, instead of calling the original function again
 *
 * Results are not cached, once the promise has returned, the next call will result in a fresh call
 *
 * Read more at https://github.com/bitwarden/jslib/pull/7
 */
function bw_sequentialize(cacheKey) {
    return (target, propertyKey, descriptor) => {
        const originalMethod = descriptor.value;
        return {
            value: function (...args) {
                const cache = bw_getCache(this);
                const argsCacheKey = cacheKey(args);
                let response = cache.get(argsCacheKey);
                if (response != null) {
                    return response;
                }
                const onFinally = () => {
                    cache.delete(argsCacheKey);
                    if (cache.size === 0) {
                        bw_caches.delete(this);
                    }
                };
                response = originalMethod
                    .apply(this, args)
                    .then((val) => {
                    onFinally();
                    return val;
                })
                    .catch((err) => {
                    onFinally();
                    throw err;
                });
                cache.set(argsCacheKey, response);
                return response;
            },
        };
    };
}

;// ../../libs/common/src/platform/sync/core-sync.service.ts
var bw_core_sync_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






const bw_LAST_SYNC_DATE = new bw_UserKeyDefinition(bw_SYNC_DISK, "lastSync", {
    deserializer: (d) => (d != null ? new Date(d) : null),
    clearOn: ["logout"],
});
/**
 * Core SyncService Logic EXCEPT for fullSync so that implementations can differ.
 */
class bw_CoreSyncService {
    constructor(stateService, folderService, folderApiService, messageSender, logService, cipherService, collectionService, apiService, accountService, authService, sendService, sendApiService, stateProvider) {
        this.stateService = stateService;
        this.folderService = folderService;
        this.folderApiService = folderApiService;
        this.messageSender = messageSender;
        this.logService = logService;
        this.cipherService = cipherService;
        this.collectionService = collectionService;
        this.apiService = apiService;
        this.accountService = accountService;
        this.authService = authService;
        this.sendService = sendService;
        this.sendApiService = sendApiService;
        this.stateProvider = stateProvider;
        this.syncInProgress = false;
    }
    getLastSync() {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
            if (userId == null) {
                return null;
            }
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.lastSync$(userId));
        });
    }
    lastSync$(userId) {
        return this.stateProvider.getUser(userId, bw_LAST_SYNC_DATE).state$;
    }
    activeUserLastSync$() {
        return this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((a) => {
            if (a == null) {
                return (0,bw_external_rxjs_namespaceObject.of)(null);
            }
            return this.lastSync$(a.id);
        }));
    }
    setLastSync(date, userId) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_LAST_SYNC_DATE).update(() => date);
        });
    }
    syncUpsertFolder(notification, isEdit, userId) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            this.syncStarted();
            const authStatus = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService.authStatusFor$(userId));
            if (authStatus >= bw_authentication_status_AuthenticationStatus.Locked) {
                try {
                    const localFolder = yield this.folderService.get(notification.id, userId);
                    if ((!isEdit && localFolder == null) ||
                        (isEdit && localFolder != null && localFolder.revisionDate < notification.revisionDate)) {
                        const remoteFolder = yield this.folderApiService.get(notification.id);
                        if (remoteFolder != null) {
                            yield this.folderService.upsert(new bw_FolderData(remoteFolder), userId);
                            this.messageSender.send("syncedUpsertedFolder", { folderId: notification.id });
                            return this.syncCompleted(true);
                        }
                    }
                }
                catch (e) {
                    this.logService.error(e);
                }
            }
            return this.syncCompleted(false);
        });
    }
    syncDeleteFolder(notification, userId) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            this.syncStarted();
            const authStatus = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService.authStatusFor$(userId));
            if (authStatus >= bw_authentication_status_AuthenticationStatus.Locked) {
                yield this.folderService.delete(notification.id, userId);
                this.messageSender.send("syncedDeletedFolder", { folderId: notification.id });
                this.syncCompleted(true);
                return true;
            }
            return this.syncCompleted(false);
        });
    }
    syncUpsertCipher(notification, isEdit, userId) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            this.syncStarted();
            const authStatus = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService.authStatusFor$(userId));
            if (authStatus >= bw_authentication_status_AuthenticationStatus.Locked) {
                try {
                    let shouldUpdate = true;
                    const localCipher = yield this.cipherService.get(notification.id, userId);
                    if (localCipher != null && localCipher.revisionDate >= notification.revisionDate) {
                        shouldUpdate = false;
                    }
                    let checkCollections = false;
                    if (shouldUpdate) {
                        if (isEdit) {
                            shouldUpdate = localCipher != null;
                            checkCollections = true;
                        }
                        else {
                            if (notification.collectionIds == null || notification.organizationId == null) {
                                shouldUpdate = localCipher == null;
                            }
                            else {
                                shouldUpdate = false;
                                checkCollections = true;
                            }
                        }
                    }
                    if (!shouldUpdate &&
                        checkCollections &&
                        notification.organizationId != null &&
                        notification.collectionIds != null &&
                        notification.collectionIds.length > 0) {
                        const collections = yield this.collectionService.getAll();
                        if (collections != null) {
                            for (let i = 0; i < collections.length; i++) {
                                if (notification.collectionIds.indexOf(collections[i].id) > -1) {
                                    shouldUpdate = true;
                                    break;
                                }
                            }
                        }
                    }
                    if (shouldUpdate) {
                        const remoteCipher = yield this.apiService.getFullCipherDetails(notification.id);
                        if (remoteCipher != null) {
                            yield this.cipherService.upsert(new bw_CipherData(remoteCipher));
                            this.messageSender.send("syncedUpsertedCipher", { cipherId: notification.id });
                            return this.syncCompleted(true);
                        }
                    }
                }
                catch (e) {
                    if (e != null && e.statusCode === 404 && isEdit) {
                        yield this.cipherService.delete(notification.id, userId);
                        this.messageSender.send("syncedDeletedCipher", { cipherId: notification.id });
                        return this.syncCompleted(true);
                    }
                }
            }
            return this.syncCompleted(false);
        });
    }
    syncDeleteCipher(notification, userId) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            this.syncStarted();
            const authStatus = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService.authStatusFor$(userId));
            if (authStatus >= bw_authentication_status_AuthenticationStatus.Locked) {
                yield this.cipherService.delete(notification.id, userId);
                this.messageSender.send("syncedDeletedCipher", { cipherId: notification.id });
                return this.syncCompleted(true);
            }
            return this.syncCompleted(false);
        });
    }
    syncUpsertSend(notification, isEdit) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            this.syncStarted();
            const [activeUserId, status] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((a) => {
                if (a == null) {
                    (0,bw_external_rxjs_namespaceObject.of)([null, bw_authentication_status_AuthenticationStatus.LoggedOut]);
                }
                return this.authService.authStatusFor$(a.id).pipe((0,bw_external_rxjs_namespaceObject.map)((s) => [a.id, s]));
            })));
            // Process only notifications for currently active user when user is not logged out
            // TODO: once send service allows data manipulation of non-active users, this should process any received notification
            if (activeUserId === notification.userId && status !== bw_authentication_status_AuthenticationStatus.LoggedOut) {
                try {
                    const localSend = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.sendService.get$(notification.id));
                    if ((!isEdit && localSend == null) ||
                        (isEdit && localSend != null && localSend.revisionDate < notification.revisionDate)) {
                        const remoteSend = yield this.sendApiService.getSend(notification.id);
                        if (remoteSend != null) {
                            yield this.sendService.upsert(new bw_SendData(remoteSend));
                            this.messageSender.send("syncedUpsertedSend", { sendId: notification.id });
                            return this.syncCompleted(true);
                        }
                    }
                }
                catch (e) {
                    this.logService.error(e);
                }
            }
            return this.syncCompleted(false);
        });
    }
    syncDeleteSend(notification) {
        return bw_core_sync_service_awaiter(this, void 0, void 0, function* () {
            this.syncStarted();
            if (yield this.stateService.getIsAuthenticated()) {
                yield this.sendService.delete(notification.id);
                this.messageSender.send("syncedDeletedSend", { sendId: notification.id });
                this.syncCompleted(true);
                return true;
            }
            return this.syncCompleted(false);
        });
    }
    // Helpers
    syncStarted() {
        this.syncInProgress = true;
        this.messageSender.send("syncStarted");
    }
    syncCompleted(successfully) {
        this.syncInProgress = false;
        this.messageSender.send("syncCompleted", { successfully: successfully });
        return successfully;
    }
}

;// ../../libs/common/src/platform/sync/default-sync.service.ts
var bw_default_sync_service_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_default_sync_service_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};
var bw_default_sync_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore













class bw_DefaultSyncService extends bw_CoreSyncService {
    constructor(masterPasswordService, accountService, apiService, domainSettingsService, folderService, cipherService, keyService, collectionService, messageSender, policyService, sendService, logService, keyConnectorService, stateService, providerService, folderApiService, organizationService, sendApiService, userDecryptionOptionsService, avatarService, logoutCallback, billingAccountProfileStateService, tokenService, authService, stateProvider) {
        super(stateService, folderService, folderApiService, messageSender, logService, cipherService, collectionService, apiService, accountService, authService, sendService, sendApiService, stateProvider);
        this.masterPasswordService = masterPasswordService;
        this.domainSettingsService = domainSettingsService;
        this.keyService = keyService;
        this.policyService = policyService;
        this.keyConnectorService = keyConnectorService;
        this.providerService = providerService;
        this.organizationService = organizationService;
        this.userDecryptionOptionsService = userDecryptionOptionsService;
        this.avatarService = avatarService;
        this.logoutCallback = logoutCallback;
        this.billingAccountProfileStateService = billingAccountProfileStateService;
        this.tokenService = tokenService;
        this.syncInProgress = false;
    }
    fullSync(forceSync_1) {
        return bw_default_sync_service_awaiter(this, arguments, void 0, function* (forceSync, allowThrowOnError = false) {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
            this.syncStarted();
            const authStatus = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService.authStatusFor$(userId));
            if (authStatus === bw_authentication_status_AuthenticationStatus.LoggedOut) {
                return this.syncCompleted(false);
            }
            const now = new Date();
            let needsSync = false;
            try {
                needsSync = yield this.needsSyncing(forceSync);
            }
            catch (e) {
                if (allowThrowOnError) {
                    this.syncCompleted(false);
                    throw e;
                }
            }
            if (!needsSync) {
                yield this.setLastSync(now, userId);
                return this.syncCompleted(false);
            }
            try {
                yield this.apiService.refreshIdentityToken();
                const response = yield this.apiService.getSync();
                yield this.syncProfile(response.profile);
                yield this.syncFolders(response.folders, response.profile.id);
                yield this.syncCollections(response.collections, response.profile.id);
                yield this.syncCiphers(response.ciphers, response.profile.id);
                yield this.syncSends(response.sends, response.profile.id);
                yield this.syncSettings(response.domains, response.profile.id);
                yield this.syncPolicies(response.policies, response.profile.id);
                yield this.setLastSync(now, userId);
                return this.syncCompleted(true);
            }
            catch (e) {
                if (allowThrowOnError) {
                    this.syncCompleted(false);
                    throw e;
                }
                else {
                    return this.syncCompleted(false);
                }
            }
        });
    }
    needsSyncing(forceSync) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            if (forceSync) {
                return true;
            }
            const lastSync = yield this.getLastSync();
            if (lastSync == null || lastSync.getTime() === 0) {
                return true;
            }
            const response = yield this.apiService.getAccountRevisionDate();
            if (response < 0 && this.logoutCallback) {
                // Account was deleted, log out now
                yield this.logoutCallback("accountDeleted");
            }
            if (new Date(response) <= lastSync) {
                return false;
            }
            return true;
        });
    }
    syncProfile(response) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const stamp = yield this.tokenService.getSecurityStamp(response.id);
            if (stamp != null && stamp !== response.securityStamp) {
                if (this.logoutCallback != null) {
                    yield this.logoutCallback("invalidSecurityStamp");
                }
                throw new Error("Stamp has changed");
            }
            yield this.keyService.setMasterKeyEncryptedUserKey(response.key, response.id);
            yield this.keyService.setPrivateKey(response.privateKey, response.id);
            yield this.keyService.setProviderKeys(response.providers, response.id);
            yield this.keyService.setOrgKeys(response.organizations, response.providerOrganizations, response.id);
            yield this.avatarService.setSyncAvatarColor(response.id, response.avatarColor);
            yield this.tokenService.setSecurityStamp(response.securityStamp, response.id);
            yield this.accountService.setAccountEmailVerified(response.id, response.emailVerified);
            yield this.accountService.setAccountVerifyNewDeviceLogin(response.id, response.verifyDevices);
            yield this.billingAccountProfileStateService.setHasPremium(response.premiumPersonally, response.premiumFromOrganization, response.id);
            yield this.keyConnectorService.setUsesKeyConnector(response.usesKeyConnector, response.id);
            yield this.setForceSetPasswordReasonIfNeeded(response);
            const providers = {};
            response.providers.forEach((p) => {
                providers[p.id] = new bw_ProviderData(p);
            });
            yield this.providerService.save(providers, response.id);
            yield this.syncProfileOrganizations(response, response.id);
            if (yield this.keyConnectorService.userNeedsMigration(response.id)) {
                yield this.keyConnectorService.setConvertAccountRequired(true, response.id);
                this.messageSender.send("convertAccountToKeyConnector");
            }
            else {
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.keyConnectorService.removeConvertAccountRequired(response.id);
            }
        });
    }
    setForceSetPasswordReasonIfNeeded(profileResponse) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            // The `forcePasswordReset` flag indicates an admin has reset the user's password and must be updated
            if (profileResponse.forcePasswordReset) {
                yield this.masterPasswordService.setForceSetPasswordReason(bw_ForceSetPasswordReason.AdminForcePasswordReset, profileResponse.id);
            }
            const userDecryptionOptions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.userDecryptionOptionsService.userDecryptionOptionsById$(profileResponse.id));
            if (userDecryptionOptions === null || userDecryptionOptions === undefined) {
                this.logService.error("Sync: Account decryption options are null or undefined.");
            }
            // Even though TDE users should only be in a single org (per single org policy), check
            // through all orgs for the manageResetPassword permission. If they have it in any org,
            // they should be forced to set a password.
            let hasManageResetPasswordPermission = false;
            for (const org of profileResponse.organizations) {
                const isAdmin = org.type === bw_OrganizationUserType.Admin;
                const isOwner = org.type === bw_OrganizationUserType.Owner;
                // Note: apparently permissions only come down populated for custom roles.
                if (isAdmin || isOwner || (org.permissions && org.permissions.manageResetPassword)) {
                    hasManageResetPasswordPermission = true;
                    break;
                }
            }
            if (userDecryptionOptions.trustedDeviceOption !== undefined &&
                !userDecryptionOptions.hasMasterPassword &&
                hasManageResetPasswordPermission) {
                // TDE user w/out MP went from having no password reset permission to having it.
                // Must set the force password reset reason so the auth guard will redirect to the set password page.
                const userId = (_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$))) === null || _a === void 0 ? void 0 : _a.id;
                yield this.masterPasswordService.setForceSetPasswordReason(bw_ForceSetPasswordReason.TdeUserWithoutPasswordHasPasswordResetPermission, userId);
            }
        });
    }
    syncProfileOrganizations(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const organizations = {};
            response.organizations.forEach((o) => {
                organizations[o.id] = new bw_OrganizationData(o, {
                    isMember: true,
                    isProviderUser: false,
                });
            });
            response.providerOrganizations.forEach((o) => {
                if (organizations[o.id] == null) {
                    organizations[o.id] = new bw_OrganizationData(o, {
                        isMember: false,
                        isProviderUser: true,
                    });
                }
                else {
                    organizations[o.id].isProviderUser = true;
                }
            });
            yield this.organizationService.replace(organizations, userId);
        });
    }
    syncFolders(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const folders = {};
            response.forEach((f) => {
                folders[f.id] = new bw_FolderData(f);
            });
            return yield this.folderService.replace(folders, userId);
        });
    }
    syncCollections(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const collections = {};
            response.forEach((c) => {
                collections[c.id] = new bw_collection_data_CollectionData(c);
            });
            return yield this.collectionService.replace(collections, userId);
        });
    }
    syncCiphers(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const ciphers = {};
            response.forEach((c) => {
                ciphers[c.id] = new bw_CipherData(c);
            });
            return yield this.cipherService.replace(ciphers, userId);
        });
    }
    syncSends(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const sends = {};
            response.forEach((s) => {
                sends[s.id] = new bw_SendData(s);
            });
            return yield this.sendService.replace(sends, userId);
        });
    }
    syncSettings(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            let eqDomains = [];
            if (response != null && response.equivalentDomains != null) {
                eqDomains = eqDomains.concat(response.equivalentDomains);
            }
            if (response != null && response.globalEquivalentDomains != null) {
                response.globalEquivalentDomains.forEach((global) => {
                    if (global.domains.length > 0) {
                        eqDomains.push(global.domains);
                    }
                });
            }
            return this.domainSettingsService.setEquivalentDomains(eqDomains, userId);
        });
    }
    syncPolicies(response, userId) {
        return bw_default_sync_service_awaiter(this, void 0, void 0, function* () {
            const policies = {};
            if (response != null) {
                response.forEach((p) => {
                    policies[p.id] = new bw_PolicyData(p);
                });
            }
            return yield this.policyService.replace(policies, userId);
        });
    }
}
bw_default_sync_service_decorate([
    bw_sequentialize(() => "fullSync"),
    bw_default_sync_service_metadata("design:type", Function),
    bw_default_sync_service_metadata("design:paramtypes", [Boolean, Object]),
    bw_default_sync_service_metadata("design:returntype", Promise)
], bw_DefaultSyncService.prototype, "fullSync", null);

;// ../../libs/common/src/platform/sync/internal.ts



;// ../../libs/common/src/platform/misc/throttle.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
/**
 * Use as a Decorator on async functions, it will limit how many times the function can be
 * in-flight at a time.
 *
 * Calls beyond the limit will be queued, and run when one of the active calls finishes
 */
function bw_throttle(limit, throttleKey) {
    return (target, propertyKey, descriptor) => {
        const originalMethod = descriptor.value;
        const allThrottles = new Map();
        const getThrottles = (obj) => {
            let throttles = allThrottles.get(obj);
            if (throttles != null) {
                return throttles;
            }
            throttles = new Map();
            allThrottles.set(obj, throttles);
            return throttles;
        };
        return {
            value: function (...args) {
                const throttles = getThrottles(this);
                const argsThrottleKey = throttleKey(args);
                let queue = throttles.get(argsThrottleKey);
                if (queue == null) {
                    queue = [];
                    throttles.set(argsThrottleKey, queue);
                }
                return new Promise((resolve, reject) => {
                    const exec = () => {
                        const onFinally = () => {
                            queue.splice(queue.indexOf(exec), 1);
                            if (queue.length >= limit) {
                                queue[limit - 1]();
                            }
                            else if (queue.length === 0) {
                                throttles.delete(argsThrottleKey);
                                if (throttles.size === 0) {
                                    allThrottles.delete(this);
                                }
                            }
                        };
                        originalMethod
                            .apply(this, args)
                            .then((val) => {
                            onFinally();
                            return val;
                        })
                            .catch((err) => {
                            onFinally();
                            throw err;
                        })
                            .then(resolve, reject);
                    };
                    queue.push(exec);
                    if (queue.length <= limit) {
                        exec();
                    }
                });
            },
        };
    };
}

;// ../../libs/common/src/services/audit.service.ts
var bw_audit_service_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_audit_service_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};
var bw_audit_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


const bw_PwnedPasswordsApi = "https://api.pwnedpasswords.com/range/";
class bw_AuditService {
    constructor(cryptoFunctionService, apiService) {
        this.cryptoFunctionService = cryptoFunctionService;
        this.apiService = apiService;
    }
    passwordLeaked(password) {
        return bw_audit_service_awaiter(this, void 0, void 0, function* () {
            const hashBytes = yield this.cryptoFunctionService.hash(password, "sha1");
            const hash = bw_utils_Utils.fromBufferToHex(hashBytes).toUpperCase();
            const hashStart = hash.substr(0, 5);
            const hashEnding = hash.substr(5);
            const response = yield this.apiService.nativeFetch(new Request(bw_PwnedPasswordsApi + hashStart));
            const leakedHashes = yield response.text();
            const match = leakedHashes.split(/\r?\n/).find((v) => {
                return v.split(":")[0] === hashEnding;
            });
            return match != null ? parseInt(match.split(":")[1], 10) : 0;
        });
    }
    breachedAccounts(username) {
        return bw_audit_service_awaiter(this, void 0, void 0, function* () {
            try {
                return yield this.apiService.getHibpBreach(username);
            }
            catch (e) {
                const error = e;
                if (error.statusCode === 404) {
                    return [];
                }
                throw new Error();
            }
        });
    }
}
bw_audit_service_decorate([
    bw_throttle(100, () => "passwordLeaked"),
    bw_audit_service_metadata("design:type", Function),
    bw_audit_service_metadata("design:paramtypes", [String]),
    bw_audit_service_metadata("design:returntype", Promise)
], bw_AuditService.prototype, "passwordLeaked", null);

;// ../../libs/common/src/models/data/event.data.ts
class bw_EventData {
    static fromJSON(obj) {
        return Object.assign(new bw_EventData(), obj);
    }
}

;// ../../libs/common/src/services/event/key-definitions.ts


const bw_key_definitions_EVENT_COLLECTION = bw_UserKeyDefinition.array(bw_EVENT_COLLECTION_DISK, "events", {
    deserializer: (s) => bw_EventData.fromJSON(s),
    clearOn: ["logout"],
});

;// ../../libs/common/src/services/event/event-collection.service.ts
var bw_event_collection_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







class bw_EventCollectionService {
    constructor(cipherService, stateProvider, organizationService, eventUploadService, authService, accountService) {
        this.cipherService = cipherService;
        this.stateProvider = stateProvider;
        this.organizationService = organizationService;
        this.eventUploadService = eventUploadService;
        this.authService = authService;
        this.accountService = accountService;
        this.getOrgIds = (orgs) => {
            var _a, _b;
            return (_b = (_a = orgs === null || orgs === void 0 ? void 0 : orgs.filter((o) => o.useEvents)) === null || _a === void 0 ? void 0 : _a.map((x) => x.id)) !== null && _b !== void 0 ? _b : [];
        };
    }
    /** Adds an event to the active user's event collection
     *  @param eventType the event type to be added
     *  @param ciphers The collection of ciphers to log events for
     *  @param uploadImmediately in some cases the recorded events should be uploaded right after being added
     */
    collectMany(eventType_1, ciphers_1) {
        return bw_event_collection_service_awaiter(this, arguments, void 0, function* (eventType, ciphers, uploadImmediately = false) {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            const eventStore = this.stateProvider.getUser(userId, bw_key_definitions_EVENT_COLLECTION);
            if (!(yield this.shouldUpdate(userId, null, eventType, ciphers))) {
                return;
            }
            const events$ = this.organizationService.organizations$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((orgs) => this.getOrgIds(orgs)), (0,bw_external_rxjs_namespaceObject.map)((orgs) => ciphers
                .filter((c) => orgs.includes(c.organizationId))
                .map((c) => ({
                type: eventType,
                cipherId: c.id,
                date: new Date().toISOString(),
                organizationId: c.organizationId,
            }))));
            yield eventStore.update((currentEvents, newEvents) => [...(currentEvents !== null && currentEvents !== void 0 ? currentEvents : []), ...newEvents], {
                combineLatestWith: events$,
            });
            if (uploadImmediately) {
                yield this.eventUploadService.uploadEvents();
            }
        });
    }
    /** Adds an event to the active user's event collection
     *  @param eventType the event type to be added
     *  @param cipherId if provided the id of the cipher involved in the event
     *  @param uploadImmediately in some cases the recorded events should be uploaded right after being added
     *  @param organizationId the organizationId involved in the event. If the cipherId is not provided an organizationId is required
     */
    collect(eventType_1) {
        return bw_event_collection_service_awaiter(this, arguments, void 0, function* (eventType, cipherId = null, uploadImmediately = false, organizationId = null) {
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            const eventStore = this.stateProvider.getUser(userId, bw_key_definitions_EVENT_COLLECTION);
            if (!(yield this.shouldUpdate(userId, organizationId, eventType, undefined, cipherId))) {
                return;
            }
            const event = new bw_EventData();
            event.type = eventType;
            event.cipherId = cipherId;
            event.date = new Date().toISOString();
            event.organizationId = organizationId;
            yield eventStore.update((events) => {
                events = events !== null && events !== void 0 ? events : [];
                events.push(event);
                return events;
            });
            if (uploadImmediately) {
                yield this.eventUploadService.uploadEvents();
            }
        });
    }
    /** Verifies if the event collection should be updated for the provided information
     *  @param userId the active user's id
     *  @param cipherId the cipher for the event
     *  @param organizationId the organization for the event
     */
    shouldUpdate(userId_1) {
        return bw_event_collection_service_awaiter(this, arguments, void 0, function* (userId, organizationId = null, eventType = null, ciphers = [], cipherId) {
            const cipher$ = (0,bw_external_rxjs_namespaceObject.from)(this.cipherService.get(cipherId, userId));
            const orgIds$ = this.organizationService
                .organizations$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((orgs) => this.getOrgIds(orgs)));
            const [authStatus, orgIds, cipher] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)((0,bw_external_rxjs_namespaceObject.zip)(this.authService.activeAccountStatus$, orgIds$, cipher$));
            // The user must be authorized
            if (authStatus != bw_authentication_status_AuthenticationStatus.Unlocked) {
                return false;
            }
            // User must have organizations assigned to them
            if (orgIds == null || orgIds.length == 0) {
                return false;
            }
            // Individual vault export doesn't need cipher id or organization id.
            if (eventType == bw_EventType.User_ClientExportedVault) {
                return true;
            }
            // If the cipherId was provided and a cipher exists, add it to the collection
            if (cipher != null) {
                ciphers.push(new bw_CipherView(cipher));
            }
            // If no ciphers there must be an organization id provided
            if ((ciphers == null || ciphers.length == 0) && organizationId == null) {
                return false;
            }
            // If the input list of ciphers is provided. Check the ciphers to see if any
            // are in the user's org list
            if (ciphers != null && ciphers.length > 0) {
                const filtered = ciphers.filter((c) => orgIds.includes(c.organizationId));
                return filtered.length > 0;
            }
            // If the organization id is provided it must be in the user's org list
            if (organizationId != null && !orgIds.includes(organizationId)) {
                return false;
            }
            return true;
        });
    }
}

;// ../../libs/common/src/models/request/event.request.ts
class bw_EventRequest {
}

;// ../../libs/common/src/services/event/event-upload.service.ts
var bw_event_upload_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_EventUploadService {
    constructor(apiService, stateProvider, logService, authService, taskSchedulerService) {
        this.apiService = apiService;
        this.stateProvider = stateProvider;
        this.logService = logService;
        this.authService = authService;
        this.taskSchedulerService = taskSchedulerService;
        this.inited = false;
        this.taskSchedulerService.registerTaskHandler(bw_ScheduledTaskNames.eventUploadsInterval, () => this.uploadEvents());
    }
    init(checkOnInterval) {
        if (this.inited) {
            return;
        }
        this.inited = true;
        if (checkOnInterval) {
            void this.uploadEvents();
            this.taskSchedulerService.setInterval(bw_ScheduledTaskNames.eventUploadsInterval, 60 * 1000);
        }
    }
    /** Upload the event collection from state.
     *  @param userId upload events for provided user. If not active user will be used.
     */
    uploadEvents(userId) {
        return bw_event_upload_service_awaiter(this, void 0, void 0, function* () {
            if (!userId) {
                userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            }
            if (!userId) {
                return;
            }
            const isUnlocked = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.authService
                .authStatusFor$(userId)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((status) => status === bw_authentication_status_AuthenticationStatus.Unlocked)));
            if (!isUnlocked) {
                return;
            }
            const eventCollection = yield this.takeEvents(userId);
            if (eventCollection == null || eventCollection.length === 0) {
                return;
            }
            const request = eventCollection.map((e) => {
                const req = new bw_EventRequest();
                req.type = e.type;
                req.cipherId = e.cipherId;
                req.date = e.date;
                req.organizationId = e.organizationId;
                return req;
            });
            try {
                yield this.apiService.postEventsCollect(request, userId);
            }
            catch (e) {
                this.logService.error(e);
                // Add the events back to state if there was an error and they were not uploaded.
                yield this.stateProvider.setUserState(bw_key_definitions_EVENT_COLLECTION, eventCollection, userId);
            }
        });
    }
    /** Return user's events and then clear them from state
     *  @param userId the user to grab and clear events for
     */
    takeEvents(userId) {
        return bw_event_upload_service_awaiter(this, void 0, void 0, function* () {
            let taken = null;
            yield this.stateProvider.getUser(userId, bw_key_definitions_EVENT_COLLECTION).update((current) => {
                taken = current !== null && current !== void 0 ? current : [];
                return [];
            });
            return taken;
        });
    }
}

;// external "lunr"
const bw_external_lunr_namespaceObject = require("lunr");
;// ../../libs/common/src/services/search.service.ts
var bw_search_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






/**
 * The `KeyDefinition` for accessing the search index in application state.
 * The key definition is configured to clear the index when the user locks the vault.
 */
const bw_LUNR_SEARCH_INDEX = new bw_UserKeyDefinition(bw_VAULT_SEARCH_MEMORY, "searchIndex", {
    deserializer: (obj) => obj,
    clearOn: ["lock", "logout"],
});
/**
 * The `KeyDefinition` for accessing the ID of the entity currently indexed by Lunr search.
 * The key definition is configured to clear the indexed entity ID when the user locks the vault.
 */
const bw_LUNR_SEARCH_INDEXED_ENTITY_ID = new bw_UserKeyDefinition(bw_VAULT_SEARCH_MEMORY, "searchIndexedEntityId", {
    deserializer: (obj) => obj,
    clearOn: ["lock", "logout"],
});
/**
 * The `KeyDefinition` for accessing the state of Lunr search indexing, indicating whether the Lunr search index is currently being built or updating.
 * The key definition is configured to clear the indexing state when the user locks the vault.
 */
const bw_LUNR_SEARCH_INDEXING = new bw_UserKeyDefinition(bw_VAULT_SEARCH_MEMORY, "isIndexing", {
    deserializer: (obj) => obj,
    clearOn: ["lock", "logout"],
});
class bw_SearchService {
    constructor(logService, i18nService, stateProvider) {
        this.logService = logService;
        this.i18nService = i18nService;
        this.stateProvider = stateProvider;
        this.immediateSearchLocales = ["zh-CN", "zh-TW", "ja", "ko", "vi"];
        this.defaultSearchableMinLength = 2;
        this.searchableMinLength = this.defaultSearchableMinLength;
        this.i18nService.locale$.subscribe((locale) => {
            if (this.immediateSearchLocales.indexOf(locale) !== -1) {
                this.searchableMinLength = 1;
            }
            else {
                this.searchableMinLength = this.defaultSearchableMinLength;
            }
        });
        // Currently have to ensure this is only done a single time. Lunr allows you to register a function
        // multiple times but they will add a warning message to the console. The way they do that breaks when ran on a service worker.
        if (!bw_SearchService.registeredPipeline) {
            bw_SearchService.registeredPipeline = true;
            //register lunr pipeline function
            bw_external_lunr_namespaceObject.Pipeline.registerFunction(this.normalizeAccentsPipelineFunction, "normalizeAccents");
        }
    }
    searchIndexState(userId) {
        return this.stateProvider.getUser(userId, bw_LUNR_SEARCH_INDEX);
    }
    index$(userId) {
        return this.searchIndexState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((searchIndex) => (searchIndex ? bw_external_lunr_namespaceObject.Index.load(searchIndex) : null)));
    }
    searchIndexEntityIdState(userId) {
        return this.stateProvider.getUser(userId, bw_LUNR_SEARCH_INDEXED_ENTITY_ID);
    }
    indexedEntityId$(userId) {
        return this.searchIndexEntityIdState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((id) => id));
    }
    searchIsIndexingState(userId) {
        return this.stateProvider.getUser(userId, bw_LUNR_SEARCH_INDEXING);
    }
    searchIsIndexing$(userId) {
        return this.searchIsIndexingState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((indexing) => indexing !== null && indexing !== void 0 ? indexing : false));
    }
    clearIndex(userId) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            yield this.searchIndexEntityIdState(userId).update(() => null);
            yield this.searchIndexState(userId).update(() => null);
            yield this.searchIsIndexingState(userId).update(() => null);
        });
    }
    isSearchable(userId, query) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            query = bw_SearchService.normalizeSearchQuery(query);
            const index = yield this.getIndexForSearch(userId);
            const notSearchable = query == null ||
                (index == null && query.length < this.searchableMinLength) ||
                (index != null && query.length < this.searchableMinLength && query.indexOf(">") !== 0);
            return !notSearchable;
        });
    }
    indexCiphers(userId, ciphers, indexedEntityId) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            if (yield this.getIsIndexing(userId)) {
                return;
            }
            yield this.setIsIndexing(userId, true);
            yield this.setIndexedEntityIdForSearch(userId, indexedEntityId);
            const builder = new bw_external_lunr_namespaceObject.Builder();
            builder.pipeline.add(this.normalizeAccentsPipelineFunction);
            builder.ref("id");
            builder.field("shortid", { boost: 100, extractor: (c) => c.id.substr(0, 8) });
            builder.field("name", {
                boost: 10,
            });
            builder.field("subtitle", {
                boost: 5,
                extractor: (c) => {
                    if (c.subTitle != null && c.type === bw_CipherType.Card) {
                        return c.subTitle.replace(/\*/g, "");
                    }
                    return c.subTitle;
                },
            });
            builder.field("notes");
            builder.field("login.username", {
                extractor: (c) => c.type === bw_CipherType.Login && c.login != null ? c.login.username : null,
            });
            builder.field("login.uris", { boost: 2, extractor: (c) => this.uriExtractor(c) });
            builder.field("fields", { extractor: (c) => this.fieldExtractor(c, false) });
            builder.field("fields_joined", { extractor: (c) => this.fieldExtractor(c, true) });
            builder.field("attachments", {
                extractor: (c) => this.attachmentExtractor(c, false),
            });
            builder.field("attachments_joined", {
                extractor: (c) => this.attachmentExtractor(c, true),
            });
            builder.field("organizationid", { extractor: (c) => c.organizationId });
            ciphers = ciphers || [];
            ciphers.forEach((c) => builder.add(c));
            const index = builder.build();
            yield this.setIndexForSearch(userId, index.toJSON());
            yield this.setIsIndexing(userId, false);
            this.logService.info("Finished search indexing");
        });
    }
    searchCiphers(userId_1, query_1) {
        return bw_search_service_awaiter(this, arguments, void 0, function* (userId, query, filter = null, ciphers) {
            const results = [];
            if (query != null) {
                query = bw_SearchService.normalizeSearchQuery(query.trim().toLowerCase());
            }
            if (query === "") {
                query = null;
            }
            if (ciphers == null) {
                ciphers = [];
            }
            if (filter != null && Array.isArray(filter) && filter.length > 0) {
                ciphers = ciphers.filter((c) => filter.every((f) => f == null || f(c)));
            }
            else if (filter != null) {
                ciphers = ciphers.filter(filter);
            }
            if (!(yield this.isSearchable(userId, query))) {
                return ciphers;
            }
            if (yield this.getIsIndexing(userId)) {
                yield new Promise((r) => setTimeout(r, 250));
                if (yield this.getIsIndexing(userId)) {
                    yield new Promise((r) => setTimeout(r, 500));
                }
            }
            const index = yield this.getIndexForSearch(userId);
            if (index == null) {
                // Fall back to basic search if index is not available
                return this.searchCiphersBasic(ciphers, query);
            }
            const ciphersMap = new Map();
            ciphers.forEach((c) => ciphersMap.set(c.id, c));
            let searchResults = null;
            const isQueryString = query != null && query.length > 1 && query.indexOf(">") === 0;
            if (isQueryString) {
                try {
                    searchResults = index.search(query.substr(1).trim());
                }
                catch (e) {
                    this.logService.error(e);
                }
            }
            else {
                const soWild = bw_external_lunr_namespaceObject.Query.wildcard.LEADING | bw_external_lunr_namespaceObject.Query.wildcard.TRAILING;
                searchResults = index.query((q) => {
                    bw_external_lunr_namespaceObject.tokenizer(query).forEach((token) => {
                        const t = token.toString();
                        q.term(t, { fields: ["name"], wildcard: soWild });
                        q.term(t, { fields: ["subtitle"], wildcard: soWild });
                        q.term(t, { fields: ["login.uris"], wildcard: soWild });
                        q.term(t, {});
                    });
                });
            }
            if (searchResults != null) {
                searchResults.forEach((r) => {
                    if (ciphersMap.has(r.ref)) {
                        results.push(ciphersMap.get(r.ref));
                    }
                });
            }
            return results;
        });
    }
    searchCiphersBasic(ciphers, query, deleted = false) {
        query = bw_SearchService.normalizeSearchQuery(query.trim().toLowerCase());
        return ciphers.filter((c) => {
            if (deleted !== c.isDeleted) {
                return false;
            }
            if (c.name != null && c.name.toLowerCase().indexOf(query) > -1) {
                return true;
            }
            if (query.length >= 8 && c.id.startsWith(query)) {
                return true;
            }
            if (c.subTitle != null && c.subTitle.toLowerCase().indexOf(query) > -1) {
                return true;
            }
            if (c.login &&
                c.login.hasUris &&
                c.login.uris.some((loginUri) => { var _a; return ((_a = loginUri === null || loginUri === void 0 ? void 0 : loginUri.uri) === null || _a === void 0 ? void 0 : _a.toLowerCase().indexOf(query)) > -1; })) {
                return true;
            }
            return false;
        });
    }
    searchSends(sends, query) {
        query = bw_SearchService.normalizeSearchQuery(query.trim().toLocaleLowerCase());
        if (query === null) {
            return sends;
        }
        const sendsMatched = [];
        const lowPriorityMatched = [];
        sends.forEach((s) => {
            var _a, _b, _c;
            if (s.name != null && s.name.toLowerCase().indexOf(query) > -1) {
                sendsMatched.push(s);
            }
            else if (query.length >= 8 &&
                (s.id.startsWith(query) ||
                    s.accessId.toLocaleLowerCase().startsWith(query) ||
                    (((_a = s.file) === null || _a === void 0 ? void 0 : _a.id) != null && s.file.id.startsWith(query)))) {
                lowPriorityMatched.push(s);
            }
            else if (s.notes != null && s.notes.toLowerCase().indexOf(query) > -1) {
                lowPriorityMatched.push(s);
            }
            else if (((_b = s.text) === null || _b === void 0 ? void 0 : _b.text) != null && s.text.text.toLowerCase().indexOf(query) > -1) {
                lowPriorityMatched.push(s);
            }
            else if (((_c = s.file) === null || _c === void 0 ? void 0 : _c.fileName) != null && s.file.fileName.toLowerCase().indexOf(query) > -1) {
                lowPriorityMatched.push(s);
            }
        });
        return sendsMatched.concat(lowPriorityMatched);
    }
    getIndexForSearch(userId) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.index$(userId));
        });
    }
    setIndexForSearch(userId, index) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            yield this.searchIndexState(userId).update(() => index);
        });
    }
    setIndexedEntityIdForSearch(userId, indexedEntityId) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            yield this.searchIndexEntityIdState(userId).update(() => indexedEntityId);
        });
    }
    setIsIndexing(userId, indexing) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            yield this.searchIsIndexingState(userId).update(() => indexing);
        });
    }
    getIsIndexing(userId) {
        return bw_search_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.searchIsIndexing$(userId));
        });
    }
    fieldExtractor(c, joined) {
        if (!c.hasFields) {
            return null;
        }
        let fields = [];
        c.fields.forEach((f) => {
            if (f.name != null) {
                fields.push(f.name);
            }
            if (f.type === bw_FieldType.Text && f.value != null) {
                fields.push(f.value);
            }
        });
        fields = fields.filter((f) => f.trim() !== "");
        if (fields.length === 0) {
            return null;
        }
        return joined ? fields.join(" ") : fields;
    }
    attachmentExtractor(c, joined) {
        if (!c.hasAttachments) {
            return null;
        }
        let attachments = [];
        c.attachments.forEach((a) => {
            if (a != null && a.fileName != null) {
                if (joined && a.fileName.indexOf(".") > -1) {
                    attachments.push(a.fileName.substr(0, a.fileName.lastIndexOf(".")));
                }
                else {
                    attachments.push(a.fileName);
                }
            }
        });
        attachments = attachments.filter((f) => f.trim() !== "");
        if (attachments.length === 0) {
            return null;
        }
        return joined ? attachments.join(" ") : attachments;
    }
    uriExtractor(c) {
        if (c.type !== bw_CipherType.Login || c.login == null || !c.login.hasUris) {
            return null;
        }
        const uris = [];
        c.login.uris.forEach((u) => {
            if (u.uri == null || u.uri === "") {
                return;
            }
            if (u.hostname != null) {
                uris.push(u.hostname);
                return;
            }
            let uri = u.uri;
            if (u.match !== bw_UriMatchStrategy.RegularExpression) {
                const protocolIndex = uri.indexOf("://");
                if (protocolIndex > -1) {
                    uri = uri.substr(protocolIndex + 3);
                }
                const queryIndex = uri.search(/\?|&|#/);
                if (queryIndex > -1) {
                    uri = uri.substring(0, queryIndex);
                }
            }
            uris.push(uri);
        });
        return uris.length > 0 ? uris : null;
    }
    normalizeAccentsPipelineFunction(token) {
        const searchableFields = ["name", "login.username", "subtitle", "notes"];
        const fields = token.metadata["fields"];
        const checkFields = fields.every((i) => searchableFields.includes(i));
        if (checkFields) {
            return bw_SearchService.normalizeSearchQuery(token.toString());
        }
        return token;
    }
    // Remove accents/diacritics characters from text. This regex is equivalent to the Diacritic unicode property escape, i.e. it will match all diacritic characters.
    static normalizeSearchQuery(query) {
        return query === null || query === void 0 ? void 0 : query.normalize("NFD").replace(/[\u0300-\u036f]/g, "");
    }
}
bw_SearchService.registeredPipeline = false;

;// external "zxcvbn"
const bw_external_zxcvbn_namespaceObject = require("zxcvbn");
;// ../../libs/common/src/tools/password-strength/password-strength.service.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_PasswordStrengthService {
    /**
     * Calculates a password strength score using zxcvbn.
     * @param password The password to calculate the strength of.
     * @param emailInput An unparsed email address to use as user input.
     * @param userInputs An array of additional user inputs to use when calculating the strength.
     */
    getPasswordStrength(password, emailInput = null, userInputs = null) {
        if (password == null || password.length === 0) {
            return null;
        }
        const globalUserInputs = [
            "bitwarden",
            "bit",
            "warden",
            ...(userInputs !== null && userInputs !== void 0 ? userInputs : []),
            ...this.emailToUserInputs(emailInput),
        ];
        // Use a hash set to get rid of any duplicate user inputs
        const finalUserInputs = Array.from(new Set(globalUserInputs));
        const result = bw_external_zxcvbn_namespaceObject(password, finalUserInputs);
        return result;
    }
    /**
     * Convert an email address into a list of user inputs for zxcvbn by
     * taking the local part of the email address and splitting it into words.
     * @param email
     * @private
     */
    emailToUserInputs(email) {
        if (email == null || email.length === 0) {
            return [];
        }
        const atPosition = email.indexOf("@");
        if (atPosition < 0) {
            return [];
        }
        return email
            .substring(0, atPosition)
            .trim()
            .toLowerCase()
            .split(/[^A-Za-z0-9]/);
    }
}

;// ../../libs/common/src/tools/password-strength/index.ts



;// ../../libs/common/src/tools/send/models/domain/send.ts
var bw_send_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};







class bw_Send extends bw_domain_base_Domain {
    constructor(obj) {
        super();
        if (obj == null) {
            return;
        }
        this.buildDomainModel(this, obj, {
            id: null,
            accessId: null,
            name: null,
            notes: null,
            key: null,
        }, ["id", "accessId"]);
        this.type = obj.type;
        this.maxAccessCount = obj.maxAccessCount;
        this.accessCount = obj.accessCount;
        this.password = obj.password;
        this.disabled = obj.disabled;
        this.revisionDate = obj.revisionDate != null ? new Date(obj.revisionDate) : null;
        this.deletionDate = obj.deletionDate != null ? new Date(obj.deletionDate) : null;
        this.expirationDate = obj.expirationDate != null ? new Date(obj.expirationDate) : null;
        this.hideEmail = obj.hideEmail;
        switch (this.type) {
            case bw_SendType.Text:
                this.text = new bw_SendText(obj.text);
                break;
            case bw_SendType.File:
                this.file = new bw_SendFile(obj.file);
                break;
            default:
                break;
        }
    }
    decrypt() {
        return bw_send_awaiter(this, void 0, void 0, function* () {
            const model = new bw_SendView(this);
            const keyService = bw_utils_Utils.getContainerService().getKeyService();
            const encryptService = bw_utils_Utils.getContainerService().getEncryptService();
            try {
                const sendKeyEncryptionKey = yield keyService.getUserKey();
                model.key = yield encryptService.decryptToBytes(this.key, sendKeyEncryptionKey);
                model.cryptoKey = yield keyService.makeSendKey(model.key);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                // TODO: error?
            }
            yield this.decryptObj(this, model, ["name", "notes"], null, model.cryptoKey);
            switch (this.type) {
                case bw_SendType.File:
                    model.file = yield this.file.decrypt(model.cryptoKey);
                    break;
                case bw_SendType.Text:
                    model.text = yield this.text.decrypt(model.cryptoKey);
                    break;
                default:
                    break;
            }
            return model;
        });
    }
    static fromJSON(obj) {
        if (obj == null) {
            return null;
        }
        const revisionDate = obj.revisionDate == null ? null : new Date(obj.revisionDate);
        const expirationDate = obj.expirationDate == null ? null : new Date(obj.expirationDate);
        const deletionDate = obj.deletionDate == null ? null : new Date(obj.deletionDate);
        return Object.assign(new bw_Send(), obj, {
            key: bw_enc_string_EncString.fromJSON(obj.key),
            name: bw_enc_string_EncString.fromJSON(obj.name),
            notes: bw_enc_string_EncString.fromJSON(obj.notes),
            text: bw_SendText.fromJSON(obj.text),
            file: bw_SendFile.fromJSON(obj.file),
            revisionDate,
            expirationDate,
            deletionDate,
        });
    }
}

;// ../../libs/common/src/tools/send/models/api/send-file.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SendFileApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.id = this.getResponseProperty("Id");
        this.fileName = this.getResponseProperty("FileName");
        this.size = this.getResponseProperty("Size");
        this.sizeName = this.getResponseProperty("SizeName");
    }
}

;// ../../libs/common/src/tools/send/models/api/send-text.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SendTextApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.text = this.getResponseProperty("Text");
        this.hidden = this.getResponseProperty("Hidden") || false;
    }
}

;// ../../libs/common/src/tools/send/models/request/send.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_SendRequest {
    constructor(send, fileLength) {
        this.type = send.type;
        this.fileLength = fileLength;
        this.name = send.name ? send.name.encryptedString : null;
        this.notes = send.notes ? send.notes.encryptedString : null;
        this.maxAccessCount = send.maxAccessCount;
        this.expirationDate = send.expirationDate != null ? send.expirationDate.toISOString() : null;
        this.deletionDate = send.deletionDate != null ? send.deletionDate.toISOString() : null;
        this.key = send.key != null ? send.key.encryptedString : null;
        this.password = send.password;
        this.disabled = send.disabled;
        this.hideEmail = send.hideEmail;
        switch (this.type) {
            case bw_SendType.Text:
                this.text = new bw_SendTextApi();
                this.text.text = send.text.text != null ? send.text.text.encryptedString : null;
                this.text.hidden = send.text.hidden;
                break;
            case bw_SendType.File:
                this.file = new bw_SendFileApi();
                this.file.fileName = send.file.fileName != null ? send.file.fileName.encryptedString : null;
                break;
            default:
                break;
        }
    }
}

;// ../../libs/common/src/tools/send/models/response/send-access.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_send_access_response_SendAccessResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.type = this.getResponseProperty("Type");
        this.name = this.getResponseProperty("Name");
        const text = this.getResponseProperty("Text");
        if (text != null) {
            this.text = new bw_SendTextApi(text);
        }
        const file = this.getResponseProperty("File");
        if (file != null) {
            this.file = new bw_SendFileApi(file);
        }
        this.expirationDate = this.getResponseProperty("ExpirationDate");
        this.creatorIdentifier = this.getResponseProperty("CreatorIdentifier");
    }
}

;// ../../libs/common/src/tools/send/models/response/send-file-download-data.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SendFileDownloadDataResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = null;
        this.url = null;
        this.id = this.getResponseProperty("Id");
        this.url = this.getResponseProperty("Url");
    }
}

;// ../../libs/common/src/tools/send/models/response/send.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_send_response_SendResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.accessId = this.getResponseProperty("AccessId");
        this.type = this.getResponseProperty("Type");
        this.name = this.getResponseProperty("Name");
        this.notes = this.getResponseProperty("Notes");
        this.key = this.getResponseProperty("Key");
        this.maxAccessCount = this.getResponseProperty("MaxAccessCount");
        this.accessCount = this.getResponseProperty("AccessCount");
        this.revisionDate = this.getResponseProperty("RevisionDate");
        this.expirationDate = this.getResponseProperty("ExpirationDate");
        this.deletionDate = this.getResponseProperty("DeletionDate");
        this.password = this.getResponseProperty("Password");
        this.disable = this.getResponseProperty("Disabled") || false;
        this.hideEmail = this.getResponseProperty("HideEmail") || false;
        const text = this.getResponseProperty("Text");
        if (text != null) {
            this.text = new bw_SendTextApi(text);
        }
        const file = this.getResponseProperty("File");
        if (file != null) {
            this.file = new bw_SendFileApi(file);
        }
    }
}

;// ../../libs/common/src/tools/send/models/response/send-file-upload-data.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_SendFileUploadDataResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.url = null;
        this.fileUploadType = this.getResponseProperty("FileUploadType");
        const sendResponse = this.getResponseProperty("SendResponse");
        this.sendResponse = sendResponse == null ? null : new bw_send_response_SendResponse(sendResponse);
        this.url = this.getResponseProperty("Url");
    }
}

;// ../../libs/common/src/tools/send/services/send-api.service.ts
var bw_send_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};










class bw_SendApiService {
    constructor(apiService, fileUploadService, sendService) {
        this.apiService = apiService;
        this.fileUploadService = fileUploadService;
        this.sendService = sendService;
    }
    getSend(id) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/sends/" + id, null, true, true);
            return new bw_send_response_SendResponse(r);
        });
    }
    postSendAccess(id, request, apiUrl) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const addSendIdHeader = (headers) => {
                headers.set("Send-Id", id);
            };
            const r = yield this.apiService.send("POST", "/sends/access/" + id, request, false, true, apiUrl, addSendIdHeader);
            return new bw_send_access_response_SendAccessResponse(r);
        });
    }
    getSendFileDownloadData(send, request, apiUrl) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const addSendIdHeader = (headers) => {
                headers.set("Send-Id", send.id);
            };
            const r = yield this.apiService.send("POST", "/sends/" + send.id + "/access/file/" + send.file.id, request, false, true, apiUrl, addSendIdHeader);
            return new bw_SendFileDownloadDataResponse(r);
        });
    }
    getSends() {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/sends", null, true, true);
            return new bw_ListResponse(r, bw_send_response_SendResponse);
        });
    }
    postSend(request) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/sends", request, true, true);
            return new bw_send_response_SendResponse(r);
        });
    }
    postFileTypeSend(request) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/sends/file/v2", request, true, true);
            return new bw_SendFileUploadDataResponse(r);
        });
    }
    renewSendFileUploadUrl(sendId, fileId) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/sends/" + sendId + "/file/" + fileId, null, true, true);
            return new bw_SendFileUploadDataResponse(r);
        });
    }
    postSendFile(sendId, fileId, data) {
        return this.apiService.send("POST", "/sends/" + sendId + "/file/" + fileId, data, true, false);
    }
    putSend(id, request) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/sends/" + id, request, true, true);
            return new bw_send_response_SendResponse(r);
        });
    }
    putSendRemovePassword(id) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/sends/" + id + "/remove-password", null, true, true);
            return new bw_send_response_SendResponse(r);
        });
    }
    deleteSend(id) {
        return this.apiService.send("DELETE", "/sends/" + id, null, true, false);
    }
    save(sendData) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.upload(sendData);
            const data = new bw_SendData(response);
            yield this.sendService.upsert(data);
            return new bw_Send(data);
        });
    }
    delete(id) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.deleteSend(id);
            yield this.sendService.delete(id);
        });
    }
    removePassword(id) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.putSendRemovePassword(id);
            const data = new bw_SendData(response);
            yield this.sendService.upsert(data);
        });
    }
    // Send File Upload methods
    upload(sendData) {
        return bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const request = new bw_SendRequest(sendData[0], (_a = sendData[1]) === null || _a === void 0 ? void 0 : _a.buffer.byteLength);
            let response;
            if (sendData[0].id == null) {
                if (sendData[0].type === bw_SendType.Text) {
                    response = yield this.postSend(request);
                }
                else {
                    try {
                        const uploadDataResponse = yield this.postFileTypeSend(request);
                        response = uploadDataResponse.sendResponse;
                        yield this.fileUploadService.upload(uploadDataResponse, sendData[0].file.fileName, sendData[1], this.generateMethods(uploadDataResponse, response));
                    }
                    catch (e) {
                        if (e instanceof bw_ErrorResponse) {
                            throw new Error(e.getSingleMessage());
                        }
                        else {
                            throw e;
                        }
                    }
                }
                sendData[0].id = response.id;
                sendData[0].accessId = response.accessId;
            }
            else {
                response = yield this.putSend(sendData[0].id, request);
            }
            return response;
        });
    }
    generateMethods(uploadData, response) {
        return {
            postDirect: this.generatePostDirectCallback(response),
            renewFileUploadUrl: this.generateRenewFileUploadUrlCallback(response.id, response.file.id),
            rollback: this.generateRollbackCallback(response.id),
        };
    }
    generatePostDirectCallback(sendResponse) {
        return (data) => {
            return this.postSendFile(sendResponse.id, sendResponse.file.id, data);
        };
    }
    generateRenewFileUploadUrlCallback(sendId, fileId) {
        return () => bw_send_api_service_awaiter(this, void 0, void 0, function* () {
            const renewResponse = yield this.renewSendFileUploadUrl(sendId, fileId);
            return renewResponse === null || renewResponse === void 0 ? void 0 : renewResponse.url;
        });
    }
    generateRollbackCallback(sendId) {
        return () => {
            return this.deleteSend(sendId);
        };
    }
}

;// ../../libs/common/src/tools/send/services/key-definitions.ts

/** Encrypted send state stored on disk */
const bw_SEND_USER_ENCRYPTED = bw_UserKeyDefinition.record(bw_SEND_DISK, "sendUserEncrypted", {
    deserializer: (obj) => obj,
    clearOn: ["logout"],
});
/** Decrypted send state stored in memory */
const bw_SEND_USER_DECRYPTED = new bw_UserKeyDefinition(bw_SEND_MEMORY, "sendUserDecrypted", {
    deserializer: (obj) => obj,
    clearOn: ["lock"],
});

;// ../../libs/common/src/tools/send/services/send-state.provider.ts
var bw_send_state_provider_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/** State provider for sends */
class bw_SendStateProvider {
    constructor(stateProvider) {
        this.stateProvider = stateProvider;
        this.activeUserEncryptedState = this.stateProvider.getActive(bw_SEND_USER_ENCRYPTED);
        this.encryptedState$ = this.activeUserEncryptedState.combinedState$;
        this.activeUserDecryptedState = this.stateProvider.getActive(bw_SEND_USER_DECRYPTED);
        this.decryptedState$ = this.activeUserDecryptedState.state$;
    }
    /** Gets the encrypted sends from state for an active user */
    getEncryptedSends() {
        return bw_send_state_provider_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.encryptedState$);
        });
    }
    /** Sets the encrypted send state for an active user */
    setEncryptedSends(value, userId) {
        return bw_send_state_provider_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.getUser(userId, bw_SEND_USER_ENCRYPTED).update(() => value);
        });
    }
    /** Gets the decrypted sends from state for the active user */
    getDecryptedSends() {
        return bw_send_state_provider_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.decryptedState$);
        });
    }
    /** Sets the decrypted send state for an active user */
    setDecryptedSends(value) {
        return bw_send_state_provider_awaiter(this, void 0, void 0, function* () {
            yield this.activeUserDecryptedState.update(() => value);
        });
    }
}

;// ../../libs/common/src/tools/send/models/request/send-with-id.request.ts

class bw_SendWithIdRequest extends bw_SendRequest {
    constructor(send) {
        super(send);
        this.id = send.id;
    }
}

;// ../../libs/common/src/tools/send/send-kdf.ts
const bw_SEND_KDF_ITERATIONS = 100000;

;// ../../libs/common/src/tools/send/services/send.service.ts
var bw_send_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










class bw_SendService {
    constructor(keyService, i18nService, keyGenerationService, stateProvider, encryptService) {
        this.keyService = keyService;
        this.i18nService = i18nService;
        this.keyGenerationService = keyGenerationService;
        this.stateProvider = stateProvider;
        this.encryptService = encryptService;
        this.sendKeySalt = "bitwarden-send";
        this.sendKeyPurpose = "send";
        this.sends$ = this.stateProvider.encryptedState$.pipe((0,bw_external_rxjs_namespaceObject.map)(([, record]) => Object.values(record || {}).map((data) => new bw_Send(data))));
        this.sendViews$ = this.stateProvider.encryptedState$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)(([, record]) => this.decryptSends(Object.values(record || {}).map((data) => new bw_Send(data)))));
    }
    encrypt(model, file, password, key) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            let fileData = null;
            const send = new bw_Send();
            send.id = model.id;
            send.type = model.type;
            send.disabled = model.disabled;
            send.hideEmail = model.hideEmail;
            send.maxAccessCount = model.maxAccessCount;
            send.deletionDate = model.deletionDate;
            send.expirationDate = model.expirationDate;
            if (model.key == null) {
                const key = yield this.keyGenerationService.createKeyWithPurpose(128, this.sendKeyPurpose, this.sendKeySalt);
                model.key = key.material;
                model.cryptoKey = key.derivedKey;
            }
            if (password != null) {
                const passwordKey = yield this.keyGenerationService.deriveKeyFromPassword(password, model.key, new bw_PBKDF2KdfConfig(bw_SEND_KDF_ITERATIONS));
                send.password = passwordKey.keyB64;
            }
            if (key == null) {
                key = yield this.keyService.getUserKey();
            }
            send.key = yield this.encryptService.encrypt(model.key, key);
            send.name = yield this.encryptService.encrypt(model.name, model.cryptoKey);
            send.notes = yield this.encryptService.encrypt(model.notes, model.cryptoKey);
            if (send.type === bw_SendType.Text) {
                send.text = new bw_SendText();
                send.text.text = yield this.encryptService.encrypt(model.text.text, model.cryptoKey);
                send.text.hidden = model.text.hidden;
            }
            else if (send.type === bw_SendType.File) {
                send.file = new bw_SendFile();
                if (file != null) {
                    if (file instanceof ArrayBuffer) {
                        const [name, data] = yield this.encryptFileData(model.file.fileName, file, model.cryptoKey);
                        send.file.fileName = name;
                        fileData = data;
                    }
                    else {
                        fileData = yield this.parseFile(send, file, model.cryptoKey);
                    }
                }
            }
            return [send, fileData];
        });
    }
    get$(id) {
        return this.sends$.pipe((0,bw_external_rxjs_namespaceObject.distinctUntilChanged)((oldSends, newSends) => {
            const oldSend = oldSends.find((oldSend) => oldSend.id === id);
            const newSend = newSends.find((newSend) => newSend.id === id);
            if (!oldSend || !newSend) {
                // If either oldSend or newSend is not found, consider them different
                return false;
            }
            // Compare each property of the old and new Send objects
            const allPropertiesSame = Object.keys(newSend).every((key) => {
                if ((oldSend[key] != null && newSend[key] === null) ||
                    (oldSend[key] === null && newSend[key] != null)) {
                    // If a key from either old or new send is not found, and the key from the other send has a value, consider them different
                    return false;
                }
                switch (key) {
                    case "name":
                    case "notes":
                    case "key":
                        if (oldSend[key] === null && newSend[key] === null) {
                            return true;
                        }
                        return oldSend[key].encryptedString === newSend[key].encryptedString;
                    case "text":
                        if (oldSend[key].text == null && newSend[key].text == null) {
                            return true;
                        }
                        if ((oldSend[key].text != null && newSend[key].text == null) ||
                            (oldSend[key].text == null && newSend[key].text != null)) {
                            return false;
                        }
                        return oldSend[key].text.encryptedString === newSend[key].text.encryptedString;
                    case "file":
                        //Files are never updated so never will be changed.
                        return true;
                    case "revisionDate":
                    case "expirationDate":
                    case "deletionDate":
                        if (oldSend[key] === null && newSend[key] === null) {
                            return true;
                        }
                        return oldSend[key].getTime() === newSend[key].getTime();
                    default:
                        // For other properties, compare directly
                        return oldSend[key] === newSend[key];
                }
            });
            return allPropertiesSame;
        }), (0,bw_external_rxjs_namespaceObject.map)((sends) => sends.find((o) => o.id === id)));
    }
    getFromState(id) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            const [, sends] = yield this.stateProvider.getEncryptedSends();
            // eslint-disable-next-line
            if (sends == null || !sends.hasOwnProperty(id)) {
                return null;
            }
            return new bw_Send(sends[id]);
        });
    }
    getAll() {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            const [, sends] = yield this.stateProvider.getEncryptedSends();
            const response = [];
            for (const id in sends) {
                // eslint-disable-next-line
                if (sends.hasOwnProperty(id)) {
                    response.push(new bw_Send(sends[id]));
                }
            }
            return response;
        });
    }
    getAllDecryptedFromState() {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            let decSends = yield this.stateProvider.getDecryptedSends();
            if (decSends != null) {
                return decSends;
            }
            decSends = [];
            const hasKey = yield this.keyService.hasUserKey();
            if (!hasKey) {
                throw new Error("No user key found.");
            }
            const promises = [];
            const sends = yield this.getAll();
            sends.forEach((send) => {
                promises.push(send.decrypt().then((f) => decSends.push(f)));
            });
            yield Promise.all(promises);
            decSends.sort(bw_utils_Utils.getSortFunction(this.i18nService, "name"));
            yield this.stateProvider.setDecryptedSends(decSends);
            return decSends;
        });
    }
    upsert(send) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            const [userId, currentSends] = yield this.stateProvider.getEncryptedSends();
            let sends = currentSends;
            if (sends == null) {
                sends = {};
            }
            if (send instanceof bw_SendData) {
                const s = send;
                sends[s.id] = s;
            }
            else {
                send.forEach((s) => {
                    sends[s.id] = s;
                });
            }
            yield this.replace(sends, userId);
        });
    }
    delete(id) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            const [userId, sends] = yield this.stateProvider.getEncryptedSends();
            if (sends == null) {
                return;
            }
            if (typeof id === "string") {
                if (sends[id] == null) {
                    return;
                }
                delete sends[id];
            }
            else {
                id.forEach((i) => {
                    delete sends[i];
                });
            }
            yield this.replace(sends, userId);
        });
    }
    replace(sends, userId) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setEncryptedSends(sends, userId);
        });
    }
    getRotatedData(originalUserKey, newUserKey, userId) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            if (newUserKey == null) {
                throw new Error("New user key is required for rotation.");
            }
            if (originalUserKey == null) {
                throw new Error("Original user key is required for rotation.");
            }
            const req = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.sends$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)((sends) => bw_send_service_awaiter(this, void 0, void 0, function* () { return this.toRotatedKeyRequestMap(sends, originalUserKey, newUserKey); }))));
            // separate return for easier debugging
            return req;
        });
    }
    toRotatedKeyRequestMap(sends, originalUserKey, rotateUserKey) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            const requests = yield Promise.all(sends.map((send) => bw_send_service_awaiter(this, void 0, void 0, function* () {
                const sendKey = yield this.encryptService.decryptToBytes(send.key, originalUserKey);
                send.key = yield this.encryptService.encrypt(sendKey, rotateUserKey);
                return new bw_SendWithIdRequest(send);
            })));
            return requests;
        });
    }
    parseFile(send, file, key) {
        return new Promise((resolve, reject) => {
            const reader = new FileReader();
            reader.readAsArrayBuffer(file);
            reader.onload = (evt) => bw_send_service_awaiter(this, void 0, void 0, function* () {
                try {
                    const [name, data] = yield this.encryptFileData(file.name, evt.target.result, key);
                    send.file.fileName = name;
                    resolve(data);
                }
                catch (e) {
                    reject(e);
                }
            });
            reader.onerror = () => {
                reject("Error reading file.");
            };
        });
    }
    encryptFileData(fileName, data, key) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                key = yield this.keyService.getUserKey();
            }
            const encFileName = yield this.encryptService.encrypt(fileName, key);
            const encFileData = yield this.encryptService.encryptToBytes(new Uint8Array(data), key);
            return [encFileName, encFileData];
        });
    }
    decryptSends(sends) {
        return bw_send_service_awaiter(this, void 0, void 0, function* () {
            const decryptSendPromises = sends.map((s) => s.decrypt());
            const decryptedSends = yield Promise.all(decryptSendPromises);
            decryptedSends.sort(bw_utils_Utils.getSortFunction(this.i18nService, "name"));
            return decryptedSends;
        });
    }
}

;// ../../libs/common/src/vault/services/cipher-authorization.service.ts



/**
 * Service for managing user cipher authorization.
 */
class bw_CipherAuthorizationService {
}
/**
 * {@link CipherAuthorizationService}
 */
class bw_DefaultCipherAuthorizationService {
    constructor(collectionService, organizationService, accountService, configService) {
        this.collectionService = collectionService;
        this.organizationService = organizationService;
        this.accountService = accountService;
        this.configService = configService;
        this.organization$ = (cipher) => this.accountService.activeAccount$.pipe(bw_getUserId, (0,bw_external_rxjs_namespaceObject.switchMap)((userId) => this.organizationService.organizations$(userId)), (0,bw_external_rxjs_namespaceObject.map)((orgs) => orgs.find((org) => org.id === cipher.organizationId)));
    }
    /**
     *
     * {@link CipherAuthorizationService.canDeleteCipher$}
     */
    canDeleteCipher$(cipher, allowedCollections, isAdminConsoleAction) {
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.organization$(cipher),
            this.configService.getFeatureFlag$(bw_feature_flag_enum_FeatureFlag.LimitItemDeletion),
        ]).pipe((0,bw_external_rxjs_namespaceObject.switchMap)(([organization, featureFlagEnabled]) => {
            if (isAdminConsoleAction) {
                // If the user is an admin, they can delete an unassigned cipher
                if (!cipher.collectionIds || cipher.collectionIds.length === 0) {
                    return (0,bw_external_rxjs_namespaceObject.of)((organization === null || organization === void 0 ? void 0 : organization.canEditUnassignedCiphers) === true);
                }
                if (organization === null || organization === void 0 ? void 0 : organization.canEditAllCiphers) {
                    return (0,bw_external_rxjs_namespaceObject.of)(true);
                }
            }
            if (featureFlagEnabled) {
                return (0,bw_external_rxjs_namespaceObject.of)(cipher.permissions.delete);
            }
            if (cipher.organizationId == null) {
                return (0,bw_external_rxjs_namespaceObject.of)(true);
            }
            return this.collectionService
                .decryptedCollectionViews$(cipher.collectionIds)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((allCollections) => {
                const shouldFilter = allowedCollections === null || allowedCollections === void 0 ? void 0 : allowedCollections.some(Boolean);
                const collections = shouldFilter
                    ? allCollections.filter((c) => allowedCollections === null || allowedCollections === void 0 ? void 0 : allowedCollections.includes(c.id))
                    : allCollections;
                return collections.some((collection) => collection.manage);
            }));
        }));
    }
    /**
     *
     * {@link CipherAuthorizationService.canRestoreCipher$}
     */
    canRestoreCipher$(cipher, isAdminConsoleAction) {
        return this.organization$(cipher).pipe((0,bw_external_rxjs_namespaceObject.map)((organization) => {
            if (isAdminConsoleAction) {
                // If the user is an admin, they can restore an unassigned cipher
                if (!cipher.collectionIds || cipher.collectionIds.length === 0) {
                    return (organization === null || organization === void 0 ? void 0 : organization.canEditUnassignedCiphers) === true;
                }
                if (organization === null || organization === void 0 ? void 0 : organization.canEditAllCiphers) {
                    return true;
                }
            }
            return cipher.permissions.restore;
        }));
    }
    /**
     * {@link CipherAuthorizationService.canCloneCipher$}
     */
    canCloneCipher$(cipher, isAdminConsoleAction) {
        if (cipher.organizationId == null) {
            return (0,bw_external_rxjs_namespaceObject.of)(true);
        }
        return this.organization$(cipher).pipe((0,bw_external_rxjs_namespaceObject.switchMap)((organization) => {
            var _a;
            // Admins and custom users can always clone when in the Admin Console
            if (isAdminConsoleAction &&
                organization &&
                (organization.isAdmin || ((_a = organization.permissions) === null || _a === void 0 ? void 0 : _a.editAnyCollection))) {
                return (0,bw_external_rxjs_namespaceObject.of)(true);
            }
            return this.collectionService
                .decryptedCollectionViews$(cipher.collectionIds)
                .pipe((0,bw_external_rxjs_namespaceObject.map)((allCollections) => allCollections.some((collection) => collection.manage)));
        }), (0,bw_external_rxjs_namespaceObject.shareReplay)({ bufferSize: 1, refCount: false }));
    }
}

;// ../../libs/common/src/vault/models/domain/sorted-ciphers-cache.ts
const bw_CacheTTL = 3000;
class bw_SortedCiphersCache {
    constructor(comparator) {
        this.comparator = comparator;
        this.sortedCiphersByUrl = new Map();
        this.timeouts = new Map();
    }
    isCached(url) {
        return this.sortedCiphersByUrl.has(url);
    }
    addCiphers(url, ciphers) {
        ciphers.sort(this.comparator);
        this.sortedCiphersByUrl.set(url, new bw_Ciphers(ciphers));
        this.resetTimer(url);
    }
    getLastUsed(url) {
        this.resetTimer(url);
        return this.isCached(url) ? this.sortedCiphersByUrl.get(url).getLastUsed() : null;
    }
    getLastLaunched(url) {
        return this.isCached(url) ? this.sortedCiphersByUrl.get(url).getLastLaunched() : null;
    }
    getNext(url) {
        this.resetTimer(url);
        return this.isCached(url) ? this.sortedCiphersByUrl.get(url).getNext() : null;
    }
    updateLastUsedIndex(url) {
        if (this.isCached(url)) {
            this.sortedCiphersByUrl.get(url).updateLastUsedIndex();
        }
    }
    clear() {
        this.sortedCiphersByUrl.clear();
        this.timeouts.clear();
    }
    resetTimer(url) {
        clearTimeout(this.timeouts.get(url));
        this.timeouts.set(url, setTimeout(() => {
            this.sortedCiphersByUrl.delete(url);
            this.timeouts.delete(url);
        }, bw_CacheTTL));
    }
}
class bw_Ciphers {
    constructor(ciphers) {
        this.ciphers = ciphers;
        this.lastUsedIndex = -1;
    }
    getLastUsed() {
        this.lastUsedIndex = Math.max(this.lastUsedIndex, 0);
        return this.ciphers[this.lastUsedIndex];
    }
    getLastLaunched() {
        const usedCiphers = this.ciphers.filter((cipher) => { var _a; return (_a = cipher.localData) === null || _a === void 0 ? void 0 : _a.lastLaunched; });
        const sortedCiphers = usedCiphers.sort((x, y) => y.localData.lastLaunched.valueOf() - x.localData.lastLaunched.valueOf());
        return sortedCiphers[0];
    }
    getNextIndex() {
        return (this.lastUsedIndex + 1) % this.ciphers.length;
    }
    getNext() {
        return this.ciphers[this.getNextIndex()];
    }
    updateLastUsedIndex() {
        this.lastUsedIndex = this.getNextIndex();
    }
}

;// ../../libs/common/src/vault/models/request/cipher-bulk-delete.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_CipherBulkDeleteRequest {
    constructor(ids, organizationId) {
        this.ids = ids == null ? [] : ids;
        this.organizationId = organizationId;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-bulk-move.request.ts
class bw_CipherBulkMoveRequest {
    constructor(ids, folderId) {
        this.ids = ids == null ? [] : ids;
        this.folderId = folderId;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-bulk-restore.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_CipherBulkRestoreRequest {
    constructor(ids, organizationId) {
        this.ids = ids == null ? [] : ids;
        this.organizationId = organizationId;
    }
}

;// ../../libs/common/src/vault/models/api/card.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_CardApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.cardholderName = this.getResponseProperty("CardholderName");
        this.brand = this.getResponseProperty("Brand");
        this.number = this.getResponseProperty("Number");
        this.expMonth = this.getResponseProperty("ExpMonth");
        this.expYear = this.getResponseProperty("ExpYear");
        this.code = this.getResponseProperty("Code");
    }
}

;// ../../libs/common/src/vault/models/api/fido2-credential.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_Fido2CredentialApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.credentialId = this.getResponseProperty("CredentialId");
        this.keyType = this.getResponseProperty("KeyType");
        this.keyAlgorithm = this.getResponseProperty("KeyAlgorithm");
        this.keyCurve = this.getResponseProperty("KeyCurve");
        this.keyValue = this.getResponseProperty("keyValue");
        this.rpId = this.getResponseProperty("RpId");
        this.userHandle = this.getResponseProperty("UserHandle");
        this.userName = this.getResponseProperty("UserName");
        this.counter = this.getResponseProperty("Counter");
        this.rpName = this.getResponseProperty("RpName");
        this.userDisplayName = this.getResponseProperty("UserDisplayName");
        this.discoverable = this.getResponseProperty("Discoverable");
        this.creationDate = this.getResponseProperty("CreationDate");
    }
}

;// ../../libs/common/src/vault/models/api/field.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_FieldApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.type = this.getResponseProperty("Type");
        this.name = this.getResponseProperty("Name");
        this.value = this.getResponseProperty("Value");
        this.linkedId = this.getResponseProperty("linkedId");
    }
}

;// ../../libs/common/src/vault/models/api/identity.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_IdentityApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.title = this.getResponseProperty("Title");
        this.firstName = this.getResponseProperty("FirstName");
        this.middleName = this.getResponseProperty("MiddleName");
        this.lastName = this.getResponseProperty("LastName");
        this.address1 = this.getResponseProperty("Address1");
        this.address2 = this.getResponseProperty("Address2");
        this.address3 = this.getResponseProperty("Address3");
        this.city = this.getResponseProperty("City");
        this.state = this.getResponseProperty("State");
        this.postalCode = this.getResponseProperty("PostalCode");
        this.country = this.getResponseProperty("Country");
        this.company = this.getResponseProperty("Company");
        this.email = this.getResponseProperty("Email");
        this.phone = this.getResponseProperty("Phone");
        this.ssn = this.getResponseProperty("SSN");
        this.username = this.getResponseProperty("Username");
        this.passportNumber = this.getResponseProperty("PassportNumber");
        this.licenseNumber = this.getResponseProperty("LicenseNumber");
    }
}

;// ../../libs/common/src/vault/models/api/login-uri.api.ts

class bw_LoginUriApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        this.match = null;
        if (data == null) {
            return;
        }
        this.uri = this.getResponseProperty("Uri");
        this.uriChecksum = this.getResponseProperty("UriChecksum");
        const match = this.getResponseProperty("Match");
        this.match = match != null ? match : null;
    }
}

;// ../../libs/common/src/vault/models/api/login.api.ts



class bw_LoginApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.username = this.getResponseProperty("Username");
        this.password = this.getResponseProperty("Password");
        this.passwordRevisionDate = this.getResponseProperty("PasswordRevisionDate");
        this.totp = this.getResponseProperty("Totp");
        this.autofillOnPageLoad = this.getResponseProperty("AutofillOnPageLoad");
        const uris = this.getResponseProperty("Uris");
        if (uris != null) {
            this.uris = uris.map((u) => new bw_LoginUriApi(u));
        }
        const fido2Credentials = this.getResponseProperty("Fido2Credentials");
        if (fido2Credentials != null) {
            this.fido2Credentials = fido2Credentials.map((key) => new bw_Fido2CredentialApi(key));
        }
    }
}

;// ../../libs/common/src/vault/models/api/secure-note.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SecureNoteApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.type = this.getResponseProperty("Type");
    }
}

;// ../../libs/common/src/vault/models/api/ssh-key.api.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

class bw_SshKeyApi extends bw_BaseResponse {
    constructor(data = null) {
        super(data);
        if (data == null) {
            return;
        }
        this.privateKey = this.getResponseProperty("PrivateKey");
        this.publicKey = this.getResponseProperty("PublicKey");
        this.keyFingerprint = this.getResponseProperty("KeyFingerprint");
    }
}

;// ../../libs/common/src/vault/models/request/attachment.request.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore
class bw_AttachmentRequest {
}

;// ../../libs/common/src/vault/models/request/cipher.request.ts










class bw_CipherRequest {
    constructor(cipher) {
        var _a, _b, _c;
        this.type = cipher.type;
        this.folderId = cipher.folderId;
        this.organizationId = cipher.organizationId;
        this.name = cipher.name ? cipher.name.encryptedString : null;
        this.notes = cipher.notes ? cipher.notes.encryptedString : null;
        this.favorite = cipher.favorite;
        this.lastKnownRevisionDate = cipher.revisionDate;
        this.reprompt = cipher.reprompt;
        this.key = (_a = cipher.key) === null || _a === void 0 ? void 0 : _a.encryptedString;
        switch (this.type) {
            case bw_CipherType.Login:
                this.login = new bw_LoginApi();
                this.login.uris =
                    (_c = (_b = cipher.login.uris) === null || _b === void 0 ? void 0 : _b.map((u) => {
                        const uri = new bw_LoginUriApi();
                        uri.uri = u.uri != null ? u.uri.encryptedString : null;
                        uri.match = u.match != null ? u.match : null;
                        uri.uriChecksum = u.uriChecksum != null ? u.uriChecksum.encryptedString : null;
                        return uri;
                    })) !== null && _c !== void 0 ? _c : [];
                this.login.username = cipher.login.username ? cipher.login.username.encryptedString : null;
                this.login.password = cipher.login.password ? cipher.login.password.encryptedString : null;
                this.login.passwordRevisionDate =
                    cipher.login.passwordRevisionDate != null
                        ? cipher.login.passwordRevisionDate.toISOString()
                        : null;
                this.login.totp = cipher.login.totp ? cipher.login.totp.encryptedString : null;
                this.login.autofillOnPageLoad = cipher.login.autofillOnPageLoad;
                if (cipher.login.fido2Credentials != null) {
                    this.login.fido2Credentials = cipher.login.fido2Credentials.map((key) => {
                        const keyApi = new bw_Fido2CredentialApi();
                        keyApi.credentialId =
                            key.credentialId != null ? key.credentialId.encryptedString : null;
                        keyApi.keyType =
                            key.keyType != null ? key.keyType.encryptedString : null;
                        keyApi.keyAlgorithm =
                            key.keyAlgorithm != null ? key.keyAlgorithm.encryptedString : null;
                        keyApi.keyCurve =
                            key.keyCurve != null ? key.keyCurve.encryptedString : null;
                        keyApi.keyValue = key.keyValue != null ? key.keyValue.encryptedString : null;
                        keyApi.rpId = key.rpId != null ? key.rpId.encryptedString : null;
                        keyApi.rpName = key.rpName != null ? key.rpName.encryptedString : null;
                        keyApi.counter = key.counter != null ? key.counter.encryptedString : null;
                        keyApi.userHandle = key.userHandle != null ? key.userHandle.encryptedString : null;
                        keyApi.userName = key.userName != null ? key.userName.encryptedString : null;
                        keyApi.userDisplayName =
                            key.userDisplayName != null ? key.userDisplayName.encryptedString : null;
                        keyApi.discoverable =
                            key.discoverable != null ? key.discoverable.encryptedString : null;
                        keyApi.creationDate = key.creationDate != null ? key.creationDate.toISOString() : null;
                        return keyApi;
                    });
                }
                break;
            case bw_CipherType.SecureNote:
                this.secureNote = new bw_SecureNoteApi();
                this.secureNote.type = cipher.secureNote.type;
                break;
            case bw_CipherType.SshKey:
                this.sshKey = new bw_SshKeyApi();
                this.sshKey.privateKey =
                    cipher.sshKey.privateKey != null ? cipher.sshKey.privateKey.encryptedString : null;
                this.sshKey.publicKey =
                    cipher.sshKey.publicKey != null ? cipher.sshKey.publicKey.encryptedString : null;
                this.sshKey.keyFingerprint =
                    cipher.sshKey.keyFingerprint != null
                        ? cipher.sshKey.keyFingerprint.encryptedString
                        : null;
                break;
            case bw_CipherType.Card:
                this.card = new bw_CardApi();
                this.card.cardholderName =
                    cipher.card.cardholderName != null ? cipher.card.cardholderName.encryptedString : null;
                this.card.brand = cipher.card.brand != null ? cipher.card.brand.encryptedString : null;
                this.card.number = cipher.card.number != null ? cipher.card.number.encryptedString : null;
                this.card.expMonth =
                    cipher.card.expMonth != null ? cipher.card.expMonth.encryptedString : null;
                this.card.expYear =
                    cipher.card.expYear != null ? cipher.card.expYear.encryptedString : null;
                this.card.code = cipher.card.code != null ? cipher.card.code.encryptedString : null;
                break;
            case bw_CipherType.Identity:
                this.identity = new bw_IdentityApi();
                this.identity.title =
                    cipher.identity.title != null ? cipher.identity.title.encryptedString : null;
                this.identity.firstName =
                    cipher.identity.firstName != null ? cipher.identity.firstName.encryptedString : null;
                this.identity.middleName =
                    cipher.identity.middleName != null ? cipher.identity.middleName.encryptedString : null;
                this.identity.lastName =
                    cipher.identity.lastName != null ? cipher.identity.lastName.encryptedString : null;
                this.identity.address1 =
                    cipher.identity.address1 != null ? cipher.identity.address1.encryptedString : null;
                this.identity.address2 =
                    cipher.identity.address2 != null ? cipher.identity.address2.encryptedString : null;
                this.identity.address3 =
                    cipher.identity.address3 != null ? cipher.identity.address3.encryptedString : null;
                this.identity.city =
                    cipher.identity.city != null ? cipher.identity.city.encryptedString : null;
                this.identity.state =
                    cipher.identity.state != null ? cipher.identity.state.encryptedString : null;
                this.identity.postalCode =
                    cipher.identity.postalCode != null ? cipher.identity.postalCode.encryptedString : null;
                this.identity.country =
                    cipher.identity.country != null ? cipher.identity.country.encryptedString : null;
                this.identity.company =
                    cipher.identity.company != null ? cipher.identity.company.encryptedString : null;
                this.identity.email =
                    cipher.identity.email != null ? cipher.identity.email.encryptedString : null;
                this.identity.phone =
                    cipher.identity.phone != null ? cipher.identity.phone.encryptedString : null;
                this.identity.ssn =
                    cipher.identity.ssn != null ? cipher.identity.ssn.encryptedString : null;
                this.identity.username =
                    cipher.identity.username != null ? cipher.identity.username.encryptedString : null;
                this.identity.passportNumber =
                    cipher.identity.passportNumber != null
                        ? cipher.identity.passportNumber.encryptedString
                        : null;
                this.identity.licenseNumber =
                    cipher.identity.licenseNumber != null
                        ? cipher.identity.licenseNumber.encryptedString
                        : null;
                break;
            default:
                break;
        }
        if (cipher.fields != null) {
            this.fields = cipher.fields.map((f) => {
                const field = new bw_FieldApi();
                field.type = f.type;
                field.name = f.name ? f.name.encryptedString : null;
                field.value = f.value ? f.value.encryptedString : null;
                field.linkedId = f.linkedId;
                return field;
            });
        }
        if (cipher.passwordHistory != null) {
            this.passwordHistory = [];
            cipher.passwordHistory.forEach((ph) => {
                this.passwordHistory.push({
                    lastUsedDate: ph.lastUsedDate,
                    password: ph.password ? ph.password.encryptedString : null,
                });
            });
        }
        if (cipher.attachments != null) {
            this.attachments = {};
            this.attachments2 = {};
            cipher.attachments.forEach((attachment) => {
                const fileName = attachment.fileName ? attachment.fileName.encryptedString : null;
                this.attachments[attachment.id] = fileName;
                const attachmentRequest = new bw_AttachmentRequest();
                attachmentRequest.fileName = fileName;
                if (attachment.key != null) {
                    attachmentRequest.key = attachment.key.encryptedString;
                }
                this.attachments2[attachment.id] = attachmentRequest;
            });
        }
    }
}

;// ../../libs/common/src/vault/models/request/cipher-with-id.request.ts

class bw_CipherWithIdRequest extends bw_CipherRequest {
    constructor(cipher) {
        super(cipher);
        this.id = cipher.id;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-bulk-share.request.ts

class bw_CipherBulkShareRequest {
    constructor(ciphers, collectionIds) {
        if (ciphers != null) {
            this.ciphers = [];
            ciphers.forEach((c) => {
                this.ciphers.push(new bw_CipherWithIdRequest(c));
            });
        }
        this.collectionIds = collectionIds;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-bulk-update-collections.request.ts
class bw_CipherBulkUpdateCollectionsRequest {
    constructor(organizationId, cipherIds, collectionIds, removeCollections = false) {
        this.organizationId = organizationId;
        this.cipherIds = cipherIds;
        this.collectionIds = collectionIds;
        this.removeCollections = removeCollections;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-collections.request.ts
class bw_CipherCollectionsRequest {
    constructor(collectionIds) {
        this.collectionIds = collectionIds == null ? [] : collectionIds;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-create.request.ts

class bw_CipherCreateRequest {
    constructor(cipher) {
        this.cipher = new bw_CipherRequest(cipher);
        this.collectionIds = cipher.collectionIds;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-partial.request.ts
class bw_CipherPartialRequest {
    constructor(cipher) {
        this.folderId = cipher.folderId;
        this.favorite = cipher.favorite;
    }
}

;// ../../libs/common/src/vault/models/request/cipher-share.request.ts

class bw_CipherShareRequest {
    constructor(cipher) {
        this.cipher = new bw_CipherRequest(cipher);
        this.collectionIds = cipher.collectionIds;
    }
}

;// ../../libs/common/src/vault/services/key-state/ciphers.state.ts



const bw_ENCRYPTED_CIPHERS = bw_UserKeyDefinition.record(bw_CIPHERS_DISK, "ciphers", {
    deserializer: (obj) => bw_CipherData.fromJSON(obj),
    clearOn: ["logout"],
});
const bw_DECRYPTED_CIPHERS = bw_UserKeyDefinition.record(bw_CIPHERS_MEMORY, "decryptedCiphers", {
    deserializer: (cipher) => bw_CipherView.fromJSON(cipher),
    clearOn: ["logout", "lock"],
});
const bw_FAILED_DECRYPTED_CIPHERS = bw_UserKeyDefinition.array(bw_CIPHERS_MEMORY, "failedDecryptedCiphers", {
    deserializer: (cipher) => bw_CipherView.fromJSON(cipher),
    clearOn: ["logout", "lock"],
});
const bw_LOCAL_DATA_KEY = new bw_UserKeyDefinition(bw_CIPHERS_DISK_LOCAL, "localData", {
    deserializer: (localData) => localData,
    clearOn: ["logout"],
});
const bw_ADD_EDIT_CIPHER_INFO_KEY = new bw_UserKeyDefinition(bw_CIPHERS_MEMORY, "addEditCipherInfo", {
    deserializer: (addEditCipherInfo) => {
        if (addEditCipherInfo == null) {
            return null;
        }
        const cipher = (addEditCipherInfo === null || addEditCipherInfo === void 0 ? void 0 : addEditCipherInfo.cipher.toJSON) != null
            ? addEditCipherInfo.cipher
            : bw_CipherView.fromJSON(addEditCipherInfo === null || addEditCipherInfo === void 0 ? void 0 : addEditCipherInfo.cipher);
        return { cipher, collectionIds: addEditCipherInfo.collectionIds };
    },
    clearOn: ["logout", "lock"],
});

;// ../../libs/common/src/vault/services/cipher.service.ts
var bw_cipher_service_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_cipher_service_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};
var bw_cipher_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



































const bw_CIPHER_KEY_ENC_MIN_SERVER_VER = new bw_external_semver_namespaceObject.SemVer("2024.2.0");
class bw_CipherService {
    constructor(keyService, domainSettingsService, apiService, i18nService, searchService, stateService, autofillSettingsService, encryptService, bulkEncryptService, cipherFileUploadService, configService, stateProvider, accountService) {
        this.keyService = keyService;
        this.domainSettingsService = domainSettingsService;
        this.apiService = apiService;
        this.i18nService = i18nService;
        this.searchService = searchService;
        this.stateService = stateService;
        this.autofillSettingsService = autofillSettingsService;
        this.encryptService = encryptService;
        this.bulkEncryptService = bulkEncryptService;
        this.cipherFileUploadService = cipherFileUploadService;
        this.configService = configService;
        this.stateProvider = stateProvider;
        this.accountService = accountService;
        this.sortedCiphersCache = new bw_SortedCiphersCache(this.sortCiphersByLastUsed);
        /**
         * Observable that forces the `cipherViews$` observable to re-emit with the provided value.
         * Used to let subscribers of `cipherViews$` know that the decrypted ciphers have been cleared for the active user.
         * @private
         */
        this.forceCipherViews$ = new bw_external_rxjs_namespaceObject.Subject();
    }
    localData$(userId) {
        return this.localDataState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((data) => data !== null && data !== void 0 ? data : {}));
    }
    /**
     * Observable that emits an object of encrypted ciphers for the active user.
     */
    ciphers$(userId) {
        return this.encryptedCiphersState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((ciphers) => ciphers !== null && ciphers !== void 0 ? ciphers : {}));
    }
    /**
     * Observable that emits an array of decrypted ciphers for the active user.
     * This observable will not emit until the encrypted ciphers have either been loaded from state or after sync.
     *
     * A `null` value indicates that the latest encrypted ciphers have not been decrypted yet and that
     * decryption is in progress. The latest decrypted ciphers will be emitted once decryption is complete.
     */
    cipherViews$(userId) {
        return (0,bw_external_rxjs_namespaceObject.combineLatest)([this.encryptedCiphersState(userId).state$, this.localData$(userId)]).pipe((0,bw_external_rxjs_namespaceObject.filter)(([ciphers]) => ciphers != null), // Skip if ciphers haven't been loaded yor synced yet
        (0,bw_external_rxjs_namespaceObject.switchMap)(() => (0,bw_external_rxjs_namespaceObject.merge)(this.forceCipherViews$, this.getAllDecrypted(userId))), (0,bw_external_rxjs_namespaceObject.shareReplay)({ bufferSize: 1, refCount: true }));
    }
    addEditCipherInfo$(userId) {
        return this.addEditCipherInfoState(userId).state$;
    }
    /**
     * Observable that emits an array of cipherViews that failed to decrypt. Does not emit until decryption has completed.
     *
     * An empty array indicates that all ciphers were successfully decrypted.
     */
    failedToDecryptCiphers$(userId) {
        return this.failedToDecryptCiphersState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.filter)((ciphers) => ciphers != null), (0,bw_external_rxjs_namespaceObject.switchMap)((ciphers) => (0,bw_external_rxjs_namespaceObject.merge)(this.forceCipherViews$, (0,bw_external_rxjs_namespaceObject.of)(ciphers))), (0,bw_external_rxjs_namespaceObject.shareReplay)({ bufferSize: 1, refCount: true }));
    }
    setDecryptedCipherCache(value, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            // Sometimes we might prematurely decrypt the vault and that will result in no ciphers
            // if we cache it then we may accidentally return it when it's not right, we'd rather try decryption again.
            // We still want to set null though, that is the indicator that the cache isn't valid and we should do decryption.
            if (value == null || value.length !== 0) {
                yield this.setDecryptedCiphers(value, userId);
            }
            if (this.searchService != null) {
                if (value == null) {
                    yield this.searchService.clearIndex(userId);
                }
                else {
                    yield this.searchService.indexCiphers(userId, value);
                }
            }
        });
    }
    setFailedDecryptedCiphers(cipherViews, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_FAILED_DECRYPTED_CIPHERS, cipherViews, userId);
        });
    }
    setDecryptedCiphers(value, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const cipherViews = {};
            value === null || value === void 0 ? void 0 : value.forEach((c) => {
                cipherViews[c.id] = c;
            });
            yield this.stateProvider.setUserState(bw_DECRYPTED_CIPHERS, cipherViews, userId);
        });
    }
    clearCache(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$);
            userId !== null && userId !== void 0 ? userId : (userId = activeUserId);
            yield this.clearDecryptedCiphersState(userId);
            // Force the cipherView$ observable (which always tracks the active user) to re-emit
            if (userId == activeUserId) {
                this.forceCipherViews$.next(null);
            }
        });
    }
    encrypt(model_1, userId_1, keyForCipherEncryption_1, keyForCipherKeyDecryption_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (model, userId, keyForCipherEncryption, keyForCipherKeyDecryption, originalCipher = null) {
            var _a;
            if (model.id != null) {
                if (originalCipher == null) {
                    originalCipher = yield this.get(model.id, userId);
                }
                if (originalCipher != null) {
                    yield this.updateModelfromExistingCipher(model, originalCipher, userId);
                }
                this.adjustPasswordHistoryLength(model);
            }
            const cipher = new bw_Cipher();
            cipher.id = model.id;
            cipher.folderId = model.folderId;
            cipher.favorite = model.favorite;
            cipher.organizationId = model.organizationId;
            cipher.type = model.type;
            cipher.collectionIds = model.collectionIds;
            cipher.revisionDate = model.revisionDate;
            cipher.reprompt = model.reprompt;
            cipher.edit = model.edit;
            if (yield this.getCipherKeyEncryptionEnabled()) {
                cipher.key = (_a = originalCipher === null || originalCipher === void 0 ? void 0 : originalCipher.key) !== null && _a !== void 0 ? _a : null;
                const userOrOrgKey = yield this.getKeyForCipherKeyDecryption(cipher, userId);
                // The keyForEncryption is only used for encrypting the cipher key, not the cipher itself, since cipher key encryption is enabled.
                // If the caller has provided a key for cipher key encryption, use it. Otherwise, use the user or org key.
                keyForCipherEncryption || (keyForCipherEncryption = userOrOrgKey);
                // If the caller has provided a key for cipher key decryption, use it. Otherwise, use the user or org key.
                keyForCipherKeyDecryption || (keyForCipherKeyDecryption = userOrOrgKey);
                return this.encryptCipherWithCipherKey(model, cipher, keyForCipherEncryption, keyForCipherKeyDecryption);
            }
            else {
                keyForCipherEncryption || (keyForCipherEncryption = yield this.getKeyForCipherKeyDecryption(cipher, userId));
                // We want to ensure that the cipher key is null if cipher key encryption is disabled
                // so that decryption uses the proper key.
                cipher.key = null;
                return this.encryptCipher(model, cipher, keyForCipherEncryption);
            }
        });
    }
    encryptAttachments(attachmentsModel, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if (attachmentsModel == null || attachmentsModel.length === 0) {
                return null;
            }
            const promises = [];
            const encAttachments = [];
            attachmentsModel.forEach((model) => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                const attachment = new bw_Attachment();
                attachment.id = model.id;
                attachment.size = model.size;
                attachment.sizeName = model.sizeName;
                attachment.url = model.url;
                const promise = this.encryptObjProperty(model, attachment, {
                    fileName: null,
                }, key).then(() => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                    if (model.key != null) {
                        attachment.key = yield this.encryptService.encrypt(model.key.key, key);
                    }
                    encAttachments.push(attachment);
                }));
                promises.push(promise);
            }));
            yield Promise.all(promises);
            return encAttachments;
        });
    }
    encryptFields(fieldsModel, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if (!fieldsModel || !fieldsModel.length) {
                return null;
            }
            const self = this;
            const encFields = [];
            yield fieldsModel.reduce((promise, field) => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                yield promise;
                const encField = yield self.encryptField(field, key);
                encFields.push(encField);
            }), Promise.resolve());
            return encFields;
        });
    }
    encryptField(fieldModel, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const field = new bw_Field();
            field.type = fieldModel.type;
            field.linkedId = fieldModel.linkedId;
            // normalize boolean type field values
            if (fieldModel.type === bw_FieldType.Boolean && fieldModel.value !== "true") {
                fieldModel.value = "false";
            }
            yield this.encryptObjProperty(fieldModel, field, {
                name: null,
                value: null,
            }, key);
            return field;
        });
    }
    encryptPasswordHistories(phModels, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if (!phModels || !phModels.length) {
                return null;
            }
            const self = this;
            const encPhs = [];
            yield phModels.reduce((promise, ph) => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                yield promise;
                const encPh = yield self.encryptPasswordHistory(ph, key);
                encPhs.push(encPh);
            }), Promise.resolve());
            return encPhs;
        });
    }
    encryptPasswordHistory(phModel, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const ph = new bw_Password();
            ph.lastUsedDate = phModel.lastUsedDate;
            yield this.encryptObjProperty(phModel, ph, {
                password: null,
            }, key);
            return ph;
        });
    }
    get(id, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            // eslint-disable-next-line
            if (ciphers == null || !ciphers.hasOwnProperty(id)) {
                return null;
            }
            const localData = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.localData$(userId));
            const cipherId = id;
            return new bw_Cipher(ciphers[cipherId], localData ? localData[cipherId] : null);
        });
    }
    getAll(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const localData = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.localData$(userId));
            const ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            const response = [];
            for (const id in ciphers) {
                // eslint-disable-next-line
                if (ciphers.hasOwnProperty(id)) {
                    const cipherId = id;
                    response.push(new bw_Cipher(ciphers[cipherId], localData ? localData[cipherId] : null));
                }
            }
            return response;
        });
    }
    /**
     * Decrypts all ciphers for the active user and caches them in memory. If the ciphers have already been decrypted and
     * cached, the cached ciphers are returned.
     * @deprecated Use `cipherViews$` observable instead
     */
    getAllDecrypted(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const decCiphers = yield this.getDecryptedCiphers(userId);
            if (decCiphers != null && decCiphers.length !== 0) {
                yield this.reindexCiphers(userId);
                return yield this.getDecryptedCiphers(userId);
            }
            const [newDecCiphers, failedCiphers] = yield this.decryptCiphers(yield this.getAll(userId), userId);
            yield this.setDecryptedCipherCache(newDecCiphers, userId);
            yield this.setFailedDecryptedCiphers(failedCiphers, userId);
            return newDecCiphers;
        });
    }
    getDecryptedCiphers(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            return Object.values(yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.decryptedCiphersState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((c) => c !== null && c !== void 0 ? c : {}))));
        });
    }
    /**
     * Decrypts the provided ciphers using the provided user's keys.
     * @param ciphers
     * @param userId
     * @returns Two cipher arrays, the first containing successfully decrypted ciphers and the second containing ciphers that failed to decrypt.
     * @private
     */
    decryptCiphers(ciphers, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const keys = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.cipherDecryptionKeys$(userId, true));
            if (keys == null || (keys.userKey == null && Object.keys(keys.orgKeys).length === 0)) {
                // return early if there are no keys to decrypt with
                return [[], []];
            }
            // Group ciphers by orgId or under 'null' for the user's ciphers
            const grouped = ciphers.reduce((agg, c) => {
                var _a;
                var _b;
                (_a = agg[_b = c.organizationId]) !== null && _a !== void 0 ? _a : (agg[_b] = []);
                agg[c.organizationId].push(c);
                return agg;
            }, {});
            const allCipherViews = (yield Promise.all(Object.entries(grouped).map((_a) => bw_cipher_service_awaiter(this, [_a], void 0, function* ([orgId, groupedCiphers]) {
                var _b, _c;
                if (yield this.configService.getFeatureFlag(bw_feature_flag_enum_FeatureFlag.PM4154_BulkEncryptionService)) {
                    return yield this.bulkEncryptService.decryptItems(groupedCiphers, (_b = keys.orgKeys[orgId]) !== null && _b !== void 0 ? _b : keys.userKey);
                }
                else {
                    return yield this.encryptService.decryptItems(groupedCiphers, (_c = keys.orgKeys[orgId]) !== null && _c !== void 0 ? _c : keys.userKey);
                }
            }))))
                .flat()
                .sort(this.getLocaleSortingFunction());
            // Split ciphers into two arrays, one for successfully decrypted ciphers and one for ciphers that failed to decrypt
            return allCipherViews.reduce((acc, c) => {
                if (c.decryptionFailure) {
                    acc[1].push(c);
                }
                else {
                    acc[0].push(c);
                }
                return acc;
            }, [[], []]);
        });
    }
    reindexCiphers(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const reindexRequired = this.searchService != null &&
                ((_a = (yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.searchService.indexedEntityId$(userId)))) !== null && _a !== void 0 ? _a : userId) !== userId;
            if (reindexRequired) {
                yield this.searchService.indexCiphers(userId, yield this.getDecryptedCiphers(userId), userId);
            }
        });
    }
    getAllDecryptedForGrouping(groupingId_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (groupingId, userId, folder = true) {
            const ciphers = yield this.getAllDecrypted(userId);
            return ciphers.filter((cipher) => {
                if (cipher.isDeleted) {
                    return false;
                }
                if (folder && cipher.folderId === groupingId) {
                    return true;
                }
                else if (!folder &&
                    cipher.collectionIds != null &&
                    cipher.collectionIds.indexOf(groupingId) > -1) {
                    return true;
                }
                return false;
            });
        });
    }
    getAllDecryptedForUrl(url_1, userId_1, includeOtherTypes_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (url, userId, includeOtherTypes, defaultMatch = null) {
            const ciphers = yield this.getAllDecrypted(userId);
            return yield this.filterCiphersForUrl(ciphers, url, includeOtherTypes, defaultMatch);
        });
    }
    filterCiphersForUrl(ciphers_1, url_1, includeOtherTypes_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (ciphers, url, includeOtherTypes, defaultMatch = null) {
            if (url == null && includeOtherTypes == null) {
                return [];
            }
            const equivalentDomains = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.domainSettingsService.getUrlEquivalentDomains(url));
            defaultMatch !== null && defaultMatch !== void 0 ? defaultMatch : (defaultMatch = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.domainSettingsService.defaultUriMatchStrategy$));
            return ciphers.filter((cipher) => {
                const cipherIsLogin = cipher.type === bw_CipherType.Login && cipher.login !== null;
                if (cipher.deletedDate !== null) {
                    return false;
                }
                if (Array.isArray(includeOtherTypes) &&
                    includeOtherTypes.includes(cipher.type) &&
                    !cipherIsLogin) {
                    return true;
                }
                if (cipherIsLogin) {
                    return cipher.login.matchesUri(url, equivalentDomains, defaultMatch);
                }
                return false;
            });
        });
    }
    getAllDecryptedCiphersOfType(type, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const ciphers = yield this.getAllDecrypted(userId);
            return ciphers
                .filter((cipher) => cipher.deletedDate == null && type.includes(cipher.type))
                .sort((a, b) => this.sortCiphersByLastUsedThenName(a, b));
        });
    }
    getAllFromApiForOrganization(organizationId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.apiService.getCiphersOrganization(organizationId);
            return yield this.decryptOrganizationCiphersResponse(response, organizationId);
        });
    }
    getManyFromApiForOrganization(organizationId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.apiService.send("GET", "/ciphers/organization-details/assigned?organizationId=" + organizationId, null, true, true);
            return this.decryptOrganizationCiphersResponse(response, organizationId);
        });
    }
    decryptOrganizationCiphersResponse(response, organizationId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if ((response === null || response === void 0 ? void 0 : response.data) == null || response.data.length < 1) {
                return [];
            }
            const ciphers = response.data.map((cr) => new bw_Cipher(new bw_CipherData(cr)));
            const key = yield this.keyService.getOrgKey(organizationId);
            let decCiphers = [];
            if (yield this.configService.getFeatureFlag(bw_feature_flag_enum_FeatureFlag.PM4154_BulkEncryptionService)) {
                decCiphers = yield this.bulkEncryptService.decryptItems(ciphers, key);
            }
            else {
                decCiphers = yield this.encryptService.decryptItems(ciphers, key);
            }
            decCiphers.sort(this.getLocaleSortingFunction());
            return decCiphers;
        });
    }
    getLastUsedForUrl(url_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (url, userId, autofillOnPageLoad = false) {
            return this.getCipherForUrl(url, userId, true, false, autofillOnPageLoad);
        });
    }
    getLastLaunchedForUrl(url_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (url, userId, autofillOnPageLoad = false) {
            return this.getCipherForUrl(url, userId, false, true, autofillOnPageLoad);
        });
    }
    getNextCipherForUrl(url, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            return this.getCipherForUrl(url, userId, false, false, false);
        });
    }
    getNextCardCipher(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const cacheKey = "cardCiphers";
            if (!this.sortedCiphersCache.isCached(cacheKey)) {
                const ciphers = yield this.getAllDecryptedCiphersOfType([bw_CipherType.Card], userId);
                if (!(ciphers === null || ciphers === void 0 ? void 0 : ciphers.length)) {
                    return null;
                }
                this.sortedCiphersCache.addCiphers(cacheKey, ciphers);
            }
            return this.sortedCiphersCache.getNext(cacheKey);
        });
    }
    getNextIdentityCipher(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const cacheKey = "identityCiphers";
            if (!this.sortedCiphersCache.isCached(cacheKey)) {
                const ciphers = yield this.getAllDecryptedCiphersOfType([bw_CipherType.Identity], userId);
                if (!(ciphers === null || ciphers === void 0 ? void 0 : ciphers.length)) {
                    return null;
                }
                this.sortedCiphersCache.addCiphers(cacheKey, ciphers);
            }
            return this.sortedCiphersCache.getNext(cacheKey);
        });
    }
    updateLastUsedIndexForUrl(url) {
        this.sortedCiphersCache.updateLastUsedIndex(url);
    }
    updateLastUsedDate(id, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let ciphersLocalData = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.localData$(userId));
            if (!ciphersLocalData) {
                ciphersLocalData = {};
            }
            const cipherId = id;
            if (ciphersLocalData[cipherId]) {
                ciphersLocalData[cipherId].lastUsedDate = new Date().getTime();
            }
            else {
                ciphersLocalData[cipherId] = {
                    lastUsedDate: new Date().getTime(),
                };
            }
            yield this.localDataState(userId).update(() => ciphersLocalData);
            const decryptedCipherCache = yield this.getDecryptedCiphers(userId);
            if (!decryptedCipherCache) {
                return;
            }
            for (let i = 0; i < decryptedCipherCache.length; i++) {
                const cached = decryptedCipherCache[i];
                if (cached.id === id) {
                    cached.localData = ciphersLocalData[id];
                    break;
                }
            }
            yield this.setDecryptedCiphers(decryptedCipherCache, userId);
        });
    }
    updateLastLaunchedDate(id, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let ciphersLocalData = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.localData$(userId));
            if (!ciphersLocalData) {
                ciphersLocalData = {};
            }
            const currentTime = new Date().getTime();
            ciphersLocalData[id] = {
                lastLaunched: currentTime,
                lastUsedDate: currentTime,
            };
            yield this.localDataState(userId).update(() => ciphersLocalData);
            const decryptedCipherCache = yield this.getDecryptedCiphers(userId);
            if (!decryptedCipherCache) {
                return;
            }
            for (let i = 0; i < decryptedCipherCache.length; i++) {
                const cached = decryptedCipherCache[i];
                if (cached.id === id) {
                    cached.localData = ciphersLocalData[id];
                    break;
                }
            }
            yield this.setDecryptedCiphers(decryptedCipherCache, userId);
        });
    }
    saveNeverDomain(domain) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if (domain == null) {
                return;
            }
            let domains = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.domainSettingsService.neverDomains$);
            if (!domains) {
                domains = {};
            }
            domains[domain] = null;
            yield this.domainSettingsService.setNeverDomains(domains);
        });
    }
    createWithServer(cipher, orgAdmin) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let response;
            if (orgAdmin && cipher.organizationId != null) {
                const request = new bw_CipherCreateRequest(cipher);
                response = yield this.apiService.postCipherAdmin(request);
                const data = new bw_CipherData(response, cipher.collectionIds);
                return new bw_Cipher(data);
            }
            else if (cipher.collectionIds != null) {
                const request = new bw_CipherCreateRequest(cipher);
                response = yield this.apiService.postCipherCreate(request);
            }
            else {
                const request = new bw_CipherRequest(cipher);
                response = yield this.apiService.postCipher(request);
            }
            cipher.id = response.id;
            const data = new bw_CipherData(response, cipher.collectionIds);
            const updated = yield this.upsert(data);
            // No local data for new ciphers
            return new bw_Cipher(updated[cipher.id]);
        });
    }
    updateWithServer(cipher, orgAdmin) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let response;
            if (orgAdmin) {
                const request = new bw_CipherRequest(cipher);
                response = yield this.apiService.putCipherAdmin(cipher.id, request);
                const data = new bw_CipherData(response, cipher.collectionIds);
                return new bw_Cipher(data, cipher.localData);
            }
            else if (cipher.edit) {
                const request = new bw_CipherRequest(cipher);
                response = yield this.apiService.putCipher(cipher.id, request);
            }
            else {
                const request = new bw_CipherPartialRequest(cipher);
                response = yield this.apiService.putPartialCipher(cipher.id, request);
            }
            const data = new bw_CipherData(response, cipher.collectionIds);
            const updated = yield this.upsert(data);
            // updating with server does not change local data
            return new bw_Cipher(updated[cipher.id], cipher.localData);
        });
    }
    shareWithServer(cipher, organizationId, collectionIds, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const attachmentPromises = [];
            if (cipher.attachments != null) {
                cipher.attachments.forEach((attachment) => {
                    if (attachment.key == null) {
                        attachmentPromises.push(this.shareAttachmentWithServer(attachment, cipher.id, organizationId));
                    }
                });
            }
            yield Promise.all(attachmentPromises);
            cipher.organizationId = organizationId;
            cipher.collectionIds = collectionIds;
            const encCipher = yield this.encryptSharedCipher(cipher, userId);
            const request = new bw_CipherShareRequest(encCipher);
            const response = yield this.apiService.putShareCipher(cipher.id, request);
            const data = new bw_CipherData(response, collectionIds);
            yield this.upsert(data);
            return new bw_Cipher(data, cipher.localData);
        });
    }
    shareManyWithServer(ciphers, organizationId, collectionIds, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const promises = [];
            const encCiphers = [];
            for (const cipher of ciphers) {
                cipher.organizationId = organizationId;
                cipher.collectionIds = collectionIds;
                promises.push(this.encryptSharedCipher(cipher, userId).then((c) => {
                    encCiphers.push(c);
                }));
            }
            yield Promise.all(promises);
            const request = new bw_CipherBulkShareRequest(encCiphers, collectionIds);
            try {
                yield this.apiService.putShareCiphers(request);
            }
            catch (e) {
                for (const cipher of ciphers) {
                    cipher.organizationId = null;
                    cipher.collectionIds = null;
                }
                throw e;
            }
            yield this.upsert(encCiphers.map((c) => c.toCipherData()));
        });
    }
    saveAttachmentWithServer(cipher, unencryptedFile, userId, admin = false) {
        return new Promise((resolve, reject) => {
            const reader = new FileReader();
            reader.readAsArrayBuffer(unencryptedFile);
            reader.onload = (evt) => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                try {
                    const cData = yield this.saveAttachmentRawWithServer(cipher, unencryptedFile.name, evt.target.result, userId, admin);
                    resolve(cData);
                }
                catch (e) {
                    reject(e);
                }
            });
            reader.onerror = () => {
                reject("Error reading file.");
            };
        });
    }
    saveAttachmentRawWithServer(cipher_1, filename_1, data_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (cipher, filename, data, userId, admin = false) {
            const encKey = yield this.getKeyForCipherKeyDecryption(cipher, userId);
            const cipherKeyEncryptionEnabled = yield this.getCipherKeyEncryptionEnabled();
            const cipherEncKey = cipherKeyEncryptionEnabled && cipher.key != null
                ? new bw_SymmetricCryptoKey(yield this.encryptService.decryptToBytes(cipher.key, encKey))
                : encKey;
            //if cipher key encryption is disabled but the item has an individual key,
            //then we rollback to using the user key as the main key of encryption of the item
            //in order to keep item and it's attachments with the same encryption level
            if (cipher.key != null && !cipherKeyEncryptionEnabled) {
                const model = yield cipher.decrypt(yield this.getKeyForCipherKeyDecryption(cipher, userId));
                cipher = yield this.encrypt(model, userId);
                yield this.updateWithServer(cipher);
            }
            const encFileName = yield this.encryptService.encrypt(filename, cipherEncKey);
            const dataEncKey = yield this.keyService.makeDataEncKey(cipherEncKey);
            const encData = yield this.encryptService.encryptToBytes(new Uint8Array(data), dataEncKey[0]);
            const response = yield this.cipherFileUploadService.upload(cipher, encFileName, encData, admin, dataEncKey);
            const cData = new bw_CipherData(response, cipher.collectionIds);
            if (!admin) {
                yield this.upsert(cData);
            }
            return new bw_Cipher(cData);
        });
    }
    saveCollectionsWithServer(cipher, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const request = new bw_CipherCollectionsRequest(cipher.collectionIds);
            const response = yield this.apiService.putCipherCollections(cipher.id, request);
            // The response will now check for an unavailable value. This value determines whether
            // the user still has Can Manage access to the item after updating.
            if (response.unavailable) {
                yield this.delete(cipher.id, userId);
                return;
            }
            const data = new bw_CipherData(response.cipher);
            const updated = yield this.upsert(data);
            return new bw_Cipher(updated[cipher.id], cipher.localData);
        });
    }
    saveCollectionsWithServerAdmin(cipher) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const request = new bw_CipherCollectionsRequest(cipher.collectionIds);
            const response = yield this.apiService.putCipherCollectionsAdmin(cipher.id, request);
            const data = new bw_CipherData(response);
            return new bw_Cipher(data);
        });
    }
    /**
     * Bulk update collections for many ciphers with the server
     * @param orgId
     * @param cipherIds
     * @param collectionIds
     * @param removeCollections - If true, the collectionIds will be removed from the ciphers, otherwise they will be added
     */
    bulkUpdateCollectionsWithServer(orgId_1, userId_1, cipherIds_1, collectionIds_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (orgId, userId, cipherIds, collectionIds, removeCollections = false) {
            var _a, _b;
            const request = new bw_CipherBulkUpdateCollectionsRequest(orgId, cipherIds, collectionIds, removeCollections);
            yield this.apiService.send("POST", "/ciphers/bulk-collections", request, true, false);
            // Update the local state
            const ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            for (const id of cipherIds) {
                const cipher = ciphers[id];
                if (cipher) {
                    if (removeCollections) {
                        cipher.collectionIds = (_a = cipher.collectionIds) === null || _a === void 0 ? void 0 : _a.filter((cid) => !collectionIds.includes(cid));
                    }
                    else {
                        // Append to the collectionIds if it's not already there
                        cipher.collectionIds = [...new Set([...((_b = cipher.collectionIds) !== null && _b !== void 0 ? _b : []), ...collectionIds])];
                    }
                }
            }
            yield this.clearCache();
            yield this.encryptedCiphersState(userId).update(() => ciphers);
        });
    }
    upsert(cipher) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const ciphers = cipher instanceof bw_CipherData ? [cipher] : cipher;
            const res = yield this.updateEncryptedCipherState((current) => {
                ciphers.forEach((c) => (current[c.id] = c));
                return current;
            });
            // Some state storage providers (e.g. Electron) don't update the state immediately, wait for next tick
            // Otherwise, subscribers to cipherViews$ can get stale data
            yield new Promise((resolve) => setTimeout(resolve, 0));
            return res;
        });
    }
    replace(ciphers, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            yield this.updateEncryptedCipherState(() => ciphers, userId);
        });
    }
    /**
     * Updates ciphers for the currently active user. Inactive users can only clear all ciphers, for now.
     * @param update update callback for encrypted cipher data
     * @returns
     */
    updateEncryptedCipherState(update_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (update, userId = null) {
            userId || (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            yield this.clearCache(userId);
            const updatedCiphers = yield this.stateProvider
                .getUser(userId, bw_ENCRYPTED_CIPHERS)
                .update((current) => {
                const result = update(current !== null && current !== void 0 ? current : {});
                return result;
            });
            // Some state storage providers (e.g. Electron) don't update the state immediately, wait for next tick
            // Otherwise, subscribers to cipherViews$ can get stale data
            yield new Promise((resolve) => setTimeout(resolve, 0));
            return updatedCiphers;
        });
    }
    clear(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            userId !== null && userId !== void 0 ? userId : (userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.activeUserId$));
            yield this.clearEncryptedCiphersState(userId);
            yield this.clearCache(userId);
        });
    }
    moveManyWithServer(ids, folderId, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.putMoveCiphers(new bw_CipherBulkMoveRequest(ids, folderId));
            let ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            if (ciphers == null) {
                ciphers = {};
            }
            ids.forEach((id) => {
                // eslint-disable-next-line
                if (ciphers.hasOwnProperty(id)) {
                    ciphers[id].folderId = folderId;
                }
            });
            yield this.clearCache();
            yield this.encryptedCiphersState(userId).update(() => ciphers);
        });
    }
    delete(id, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            if (ciphers == null) {
                return;
            }
            if (typeof id === "string") {
                const cipherId = id;
                if (ciphers[cipherId] == null) {
                    return;
                }
                delete ciphers[cipherId];
            }
            else {
                id.forEach((i) => {
                    delete ciphers[i];
                });
            }
            yield this.clearCache();
            yield this.encryptedCiphersState(userId).update(() => ciphers);
        });
    }
    deleteWithServer(id_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (id, userId, asAdmin = false) {
            if (asAdmin) {
                yield this.apiService.deleteCipherAdmin(id);
            }
            else {
                yield this.apiService.deleteCipher(id);
            }
            yield this.delete(id, userId);
        });
    }
    deleteManyWithServer(ids_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (ids, userId, asAdmin = false) {
            const request = new bw_CipherBulkDeleteRequest(ids);
            if (asAdmin) {
                yield this.apiService.deleteManyCiphersAdmin(request);
            }
            else {
                yield this.apiService.deleteManyCiphers(request);
            }
            yield this.delete(ids, userId);
        });
    }
    deleteAttachment(id, revisionDate, attachmentId, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            const cipherId = id;
            // eslint-disable-next-line
            if (ciphers == null || !ciphers.hasOwnProperty(id) || ciphers[cipherId].attachments == null) {
                return;
            }
            for (let i = 0; i < ciphers[cipherId].attachments.length; i++) {
                if (ciphers[cipherId].attachments[i].id === attachmentId) {
                    ciphers[cipherId].attachments.splice(i, 1);
                }
            }
            // Deleting the cipher updates the revision date on the server,
            // Update the stored `revisionDate` to match
            ciphers[cipherId].revisionDate = revisionDate;
            yield this.clearCache();
            yield this.encryptedCiphersState(userId).update(() => {
                if (ciphers == null) {
                    ciphers = {};
                }
                return ciphers;
            });
            return ciphers[cipherId];
        });
    }
    deleteAttachmentWithServer(id, attachmentId, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let cipherResponse = null;
            try {
                cipherResponse = yield this.apiService.deleteCipherAttachment(id, attachmentId);
            }
            catch (e) {
                return Promise.reject(e.getSingleMessage());
            }
            const cipherData = bw_CipherData.fromJSON(cipherResponse === null || cipherResponse === void 0 ? void 0 : cipherResponse.cipher);
            return yield this.deleteAttachment(id, cipherData.revisionDate, attachmentId, userId);
        });
    }
    sortCiphersByLastUsed(a, b) {
        const aLastUsed = a.localData && a.localData.lastUsedDate ? a.localData.lastUsedDate : null;
        const bLastUsed = b.localData && b.localData.lastUsedDate ? b.localData.lastUsedDate : null;
        const bothNotNull = aLastUsed != null && bLastUsed != null;
        if (bothNotNull && aLastUsed < bLastUsed) {
            return 1;
        }
        if (aLastUsed != null && bLastUsed == null) {
            return -1;
        }
        if (bothNotNull && aLastUsed > bLastUsed) {
            return -1;
        }
        if (bLastUsed != null && aLastUsed == null) {
            return 1;
        }
        return 0;
    }
    sortCiphersByLastUsedThenName(a, b) {
        const result = this.sortCiphersByLastUsed(a, b);
        if (result !== 0) {
            return result;
        }
        return this.getLocaleSortingFunction()(a, b);
    }
    getLocaleSortingFunction() {
        return (a, b) => {
            let aName = a.name;
            let bName = b.name;
            if (aName == null && bName != null) {
                return -1;
            }
            if (aName != null && bName == null) {
                return 1;
            }
            if (aName == null && bName == null) {
                return 0;
            }
            const result = this.i18nService.collator
                ? this.i18nService.collator.compare(aName, bName)
                : aName.localeCompare(bName);
            if (result !== 0 || a.type !== bw_CipherType.Login || b.type !== bw_CipherType.Login) {
                return result;
            }
            if (a.login.username != null) {
                aName += a.login.username;
            }
            if (b.login.username != null) {
                bName += b.login.username;
            }
            return this.i18nService.collator
                ? this.i18nService.collator.compare(aName, bName)
                : aName.localeCompare(bName);
        };
    }
    softDelete(id, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            if (ciphers == null) {
                return;
            }
            const setDeletedDate = (cipherId) => {
                if (ciphers[cipherId] == null) {
                    return;
                }
                ciphers[cipherId].deletedDate = new Date().toISOString();
            };
            if (typeof id === "string") {
                setDeletedDate(id);
            }
            else {
                id.forEach(setDeletedDate);
            }
            yield this.clearCache();
            yield this.encryptedCiphersState(userId).update(() => {
                if (ciphers == null) {
                    ciphers = {};
                }
                return ciphers;
            });
        });
    }
    softDeleteWithServer(id_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (id, userId, asAdmin = false) {
            if (asAdmin) {
                yield this.apiService.putDeleteCipherAdmin(id);
            }
            else {
                yield this.apiService.putDeleteCipher(id);
            }
            yield this.softDelete(id, userId);
        });
    }
    softDeleteManyWithServer(ids_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (ids, userId, asAdmin = false) {
            const request = new bw_CipherBulkDeleteRequest(ids);
            if (asAdmin) {
                yield this.apiService.putDeleteManyCiphersAdmin(request);
            }
            else {
                yield this.apiService.putDeleteManyCiphers(request);
            }
            yield this.softDelete(ids, userId);
        });
    }
    restore(cipher, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            let ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.ciphers$(userId));
            if (ciphers == null) {
                return;
            }
            const clearDeletedDate = (c) => {
                const cipherId = c.id;
                if (ciphers[cipherId] == null) {
                    return;
                }
                ciphers[cipherId].deletedDate = null;
                ciphers[cipherId].revisionDate = c.revisionDate;
            };
            if (cipher.constructor.name === Array.name) {
                cipher.forEach(clearDeletedDate);
            }
            else {
                clearDeletedDate(cipher);
            }
            yield this.clearCache();
            yield this.encryptedCiphersState(userId).update(() => {
                if (ciphers == null) {
                    ciphers = {};
                }
                return ciphers;
            });
        });
    }
    restoreWithServer(id_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (id, userId, asAdmin = false) {
            let response;
            if (asAdmin) {
                response = yield this.apiService.putRestoreCipherAdmin(id);
            }
            else {
                response = yield this.apiService.putRestoreCipher(id);
            }
            yield this.restore({ id: id, revisionDate: response.revisionDate }, userId);
        });
    }
    /**
     * No longer using an asAdmin Param. Org Vault bulkRestore will assess if an item is unassigned or editable
     * The Org Vault will pass those ids an array as well as the orgId when calling bulkRestore
     */
    restoreManyWithServer(ids_1, userId_1) {
        return bw_cipher_service_awaiter(this, arguments, void 0, function* (ids, userId, orgId = null) {
            let response;
            if (orgId) {
                const request = new bw_CipherBulkRestoreRequest(ids, orgId);
                response = yield this.apiService.putRestoreManyCiphersAdmin(request);
            }
            else {
                const request = new bw_CipherBulkRestoreRequest(ids);
                response = yield this.apiService.putRestoreManyCiphers(request);
            }
            const restores = [];
            for (const cipher of response.data) {
                restores.push({ id: cipher.id, revisionDate: cipher.revisionDate });
            }
            yield this.restore(restores, userId);
        });
    }
    getKeyForCipherKeyDecryption(cipher, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            return ((yield this.keyService.getOrgKey(cipher.organizationId)) ||
                (yield this.keyService.getUserKeyWithLegacySupport(userId)));
        });
    }
    setAddEditCipherInfo(value, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            yield this.addEditCipherInfoState(userId).update(() => value, {
                shouldUpdate: (current) => !(current == null && value == null),
            });
        });
    }
    getRotatedData(originalUserKey, newUserKey, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if (originalUserKey == null) {
                throw new Error("Original user key is required to rotate ciphers");
            }
            if (newUserKey == null) {
                throw new Error("New user key is required to rotate ciphers");
            }
            let encryptedCiphers = [];
            const ciphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.cipherViews$(userId));
            const failedCiphers = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.failedToDecryptCiphers$(userId));
            if (!ciphers) {
                return encryptedCiphers;
            }
            if (failedCiphers.length > 0) {
                throw new Error("Cannot rotate ciphers when decryption failures are present");
            }
            const userCiphers = ciphers.filter((c) => c.organizationId == null);
            if (userCiphers.length === 0) {
                return encryptedCiphers;
            }
            encryptedCiphers = yield Promise.all(userCiphers.map((cipher) => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                const encryptedCipher = yield this.encrypt(cipher, userId, newUserKey, originalUserKey);
                return new bw_CipherWithIdRequest(encryptedCipher);
            })));
            return encryptedCiphers;
        });
    }
    /**
     * @returns a SingleUserState
     */
    localDataState(userId) {
        return this.stateProvider.getUser(userId, bw_LOCAL_DATA_KEY);
    }
    /**
     * @returns a SingleUserState for the encrypted ciphers
     */
    encryptedCiphersState(userId) {
        return this.stateProvider.getUser(userId, bw_ENCRYPTED_CIPHERS);
    }
    /**
     * @returns a SingleUserState for the decrypted ciphers
     */
    decryptedCiphersState(userId) {
        return this.stateProvider.getUser(userId, bw_DECRYPTED_CIPHERS);
    }
    /**
     * @returns a SingleUserState for the add/edit cipher info
     */
    addEditCipherInfoState(userId) {
        return this.stateProvider.getUser(userId, bw_ADD_EDIT_CIPHER_INFO_KEY);
    }
    /**
     * @returns a SingleUserState for the failed to decrypt ciphers
     */
    failedToDecryptCiphersState(userId) {
        return this.stateProvider.getUser(userId, bw_FAILED_DECRYPTED_CIPHERS);
    }
    // Helpers
    // In the case of a cipher that is being shared with an organization, we want to decrypt the
    // cipher key with the user's key and then re-encrypt it with the organization's key.
    encryptSharedCipher(model, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const keyForCipherKeyDecryption = yield this.keyService.getUserKeyWithLegacySupport(userId);
            return yield this.encrypt(model, userId, null, keyForCipherKeyDecryption);
        });
    }
    updateModelfromExistingCipher(model, originalCipher, userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const existingCipher = yield originalCipher.decrypt(yield this.getKeyForCipherKeyDecryption(originalCipher, userId));
            model.passwordHistory = existingCipher.passwordHistory || [];
            if (model.type === bw_CipherType.Login && existingCipher.type === bw_CipherType.Login) {
                if (existingCipher.login.password != null &&
                    existingCipher.login.password !== "" &&
                    existingCipher.login.password !== model.login.password) {
                    const ph = new bw_PasswordHistoryView();
                    ph.password = existingCipher.login.password;
                    ph.lastUsedDate = model.login.passwordRevisionDate = new Date();
                    model.passwordHistory.splice(0, 0, ph);
                }
                else {
                    model.login.passwordRevisionDate = existingCipher.login.passwordRevisionDate;
                }
            }
            if (existingCipher.hasFields) {
                const existingHiddenFields = existingCipher.fields.filter((f) => f.type === bw_FieldType.Hidden &&
                    f.name != null &&
                    f.name !== "" &&
                    f.value != null &&
                    f.value !== "");
                const hiddenFields = model.fields == null
                    ? []
                    : model.fields.filter((f) => f.type === bw_FieldType.Hidden && f.name != null && f.name !== "");
                existingHiddenFields.forEach((ef) => {
                    const matchedField = hiddenFields.find((f) => f.name === ef.name);
                    if (matchedField == null || matchedField.value !== ef.value) {
                        const ph = new bw_PasswordHistoryView();
                        ph.password = ef.name + ": " + ef.value;
                        ph.lastUsedDate = new Date();
                        model.passwordHistory.splice(0, 0, ph);
                    }
                });
            }
        });
    }
    adjustPasswordHistoryLength(model) {
        if (model.passwordHistory != null && model.passwordHistory.length === 0) {
            model.passwordHistory = null;
        }
        else if (model.passwordHistory != null && model.passwordHistory.length > 5) {
            // only save last 5 history
            model.passwordHistory = model.passwordHistory.slice(0, 5);
        }
    }
    shareAttachmentWithServer(attachmentView, cipherId, organizationId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const attachmentResponse = yield this.apiService.nativeFetch(new Request(attachmentView.url, { cache: "no-store" }));
            if (attachmentResponse.status !== 200) {
                throw Error("Failed to download attachment: " + attachmentResponse.status.toString());
            }
            const encBuf = yield bw_EncArrayBuffer.fromResponse(attachmentResponse);
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            const userKey = yield this.keyService.getUserKeyWithLegacySupport(activeUserId.id);
            const decBuf = yield this.encryptService.decryptToBytes(encBuf, userKey);
            let encKey;
            encKey = yield this.keyService.getOrgKey(organizationId);
            encKey || (encKey = (yield this.keyService.getUserKeyWithLegacySupport()));
            const dataEncKey = yield this.keyService.makeDataEncKey(encKey);
            const encFileName = yield this.encryptService.encrypt(attachmentView.fileName, encKey);
            const encData = yield this.encryptService.encryptToBytes(new Uint8Array(decBuf), dataEncKey[0]);
            const fd = new FormData();
            try {
                const blob = new Blob([encData.buffer], { type: "application/octet-stream" });
                fd.append("key", dataEncKey[1].encryptedString);
                fd.append("data", blob, encFileName.encryptedString);
            }
            catch (e) {
                if (bw_utils_Utils.isNode && !bw_utils_Utils.isBrowser) {
                    fd.append("key", dataEncKey[1].encryptedString);
                    fd.append("data", Buffer.from(encData.buffer), {
                        filepath: encFileName.encryptedString,
                        contentType: "application/octet-stream",
                    });
                }
                else {
                    throw e;
                }
            }
            try {
                yield this.apiService.postShareCipherAttachment(cipherId, attachmentView.id, fd, organizationId);
            }
            catch (e) {
                throw new Error(e.getSingleMessage());
            }
        });
    }
    encryptObjProperty(model, obj, map, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const promises = [];
            const self = this;
            for (const prop in map) {
                // eslint-disable-next-line
                if (!map.hasOwnProperty(prop)) {
                    continue;
                }
                (function (theProp, theObj) {
                    const p = Promise.resolve()
                        .then(() => {
                        const modelProp = model[map[theProp] || theProp];
                        if (modelProp && modelProp !== "") {
                            return self.encryptService.encrypt(modelProp, key);
                        }
                        return null;
                    })
                        .then((val) => {
                        theObj[theProp] = val;
                    });
                    promises.push(p);
                })(prop, obj);
            }
            yield Promise.all(promises);
        });
    }
    encryptCipherData(cipher, model, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            switch (cipher.type) {
                case bw_CipherType.Login:
                    cipher.login = new bw_Login();
                    cipher.login.passwordRevisionDate = model.login.passwordRevisionDate;
                    cipher.login.autofillOnPageLoad = model.login.autofillOnPageLoad;
                    yield this.encryptObjProperty(model.login, cipher.login, {
                        username: null,
                        password: null,
                        totp: null,
                    }, key);
                    if (model.login.uris != null) {
                        cipher.login.uris = [];
                        model.login.uris = model.login.uris.filter((u) => u.uri != null && u.uri !== "");
                        for (let i = 0; i < model.login.uris.length; i++) {
                            const loginUri = new bw_LoginUri();
                            loginUri.match = model.login.uris[i].match;
                            yield this.encryptObjProperty(model.login.uris[i], loginUri, {
                                uri: null,
                            }, key);
                            const uriHash = yield this.encryptService.hash(model.login.uris[i].uri, "sha256");
                            loginUri.uriChecksum = yield this.encryptService.encrypt(uriHash, key);
                            cipher.login.uris.push(loginUri);
                        }
                    }
                    if (model.login.fido2Credentials != null) {
                        cipher.login.fido2Credentials = yield Promise.all(model.login.fido2Credentials.map((viewKey) => bw_cipher_service_awaiter(this, void 0, void 0, function* () {
                            const domainKey = new bw_Fido2Credential();
                            yield this.encryptObjProperty(viewKey, domainKey, {
                                credentialId: null,
                                keyType: null,
                                keyAlgorithm: null,
                                keyCurve: null,
                                keyValue: null,
                                rpId: null,
                                rpName: null,
                                userHandle: null,
                                userName: null,
                                userDisplayName: null,
                                origin: null,
                            }, key);
                            domainKey.counter = yield this.encryptService.encrypt(String(viewKey.counter), key);
                            domainKey.discoverable = yield this.encryptService.encrypt(String(viewKey.discoverable), key);
                            domainKey.creationDate = viewKey.creationDate;
                            return domainKey;
                        })));
                    }
                    return;
                case bw_CipherType.SecureNote:
                    cipher.secureNote = new bw_SecureNote();
                    cipher.secureNote.type = model.secureNote.type;
                    return;
                case bw_CipherType.Card:
                    cipher.card = new bw_Card();
                    yield this.encryptObjProperty(model.card, cipher.card, {
                        cardholderName: null,
                        brand: null,
                        number: null,
                        expMonth: null,
                        expYear: null,
                        code: null,
                    }, key);
                    return;
                case bw_CipherType.Identity:
                    cipher.identity = new bw_Identity();
                    yield this.encryptObjProperty(model.identity, cipher.identity, {
                        title: null,
                        firstName: null,
                        middleName: null,
                        lastName: null,
                        address1: null,
                        address2: null,
                        address3: null,
                        city: null,
                        state: null,
                        postalCode: null,
                        country: null,
                        company: null,
                        email: null,
                        phone: null,
                        ssn: null,
                        username: null,
                        passportNumber: null,
                        licenseNumber: null,
                    }, key);
                    return;
                case bw_CipherType.SshKey:
                    cipher.sshKey = new bw_SshKey();
                    yield this.encryptObjProperty(model.sshKey, cipher.sshKey, {
                        privateKey: null,
                        publicKey: null,
                        keyFingerprint: null,
                    }, key);
                    return;
                default:
                    throw new Error("Unknown cipher type.");
            }
        });
    }
    getAutofillOnPageLoadDefault() {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.autofillSettingsService.autofillOnPageLoadDefault$);
        });
    }
    getCipherForUrl(url, userId, lastUsed, lastLaunched, autofillOnPageLoad) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const cacheKey = autofillOnPageLoad ? "autofillOnPageLoad-" + url : url;
            if (!this.sortedCiphersCache.isCached(cacheKey)) {
                let ciphers = yield this.getAllDecryptedForUrl(url, userId);
                if (!ciphers) {
                    return null;
                }
                if (autofillOnPageLoad) {
                    const autofillOnPageLoadDefault = yield this.getAutofillOnPageLoadDefault();
                    ciphers = ciphers.filter((cipher) => cipher.login.autofillOnPageLoad ||
                        (cipher.login.autofillOnPageLoad == null && autofillOnPageLoadDefault !== false));
                    if (ciphers.length === 0) {
                        return null;
                    }
                }
                this.sortedCiphersCache.addCiphers(cacheKey, ciphers);
            }
            if (lastLaunched) {
                return this.sortedCiphersCache.getLastLaunched(cacheKey);
            }
            else if (lastUsed) {
                return this.sortedCiphersCache.getLastUsed(cacheKey);
            }
            else {
                return this.sortedCiphersCache.getNext(cacheKey);
            }
        });
    }
    clearEncryptedCiphersState(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_ENCRYPTED_CIPHERS, {}, userId);
        });
    }
    clearDecryptedCiphersState(userId) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            yield this.setDecryptedCiphers(null, userId);
            yield this.setFailedDecryptedCiphers(null, userId);
            this.clearSortedCiphers();
        });
    }
    clearSortedCiphers() {
        this.sortedCiphersCache.clear();
    }
    /**
     * Encrypts a cipher object.
     * @param model The cipher view model.
     * @param cipher The cipher object.
     * @param key The encryption key to encrypt with. This can be the org key, user key or cipher key, but must never be null
     */
    encryptCipher(model, cipher, key) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            if (key == null) {
                throw new Error("Key to encrypt cipher must not be null. Use the org key, user key or cipher key.");
            }
            yield Promise.all([
                this.encryptObjProperty(model, cipher, {
                    name: null,
                    notes: null,
                }, key),
                this.encryptCipherData(cipher, model, key),
                this.encryptFields(model.fields, key).then((fields) => {
                    cipher.fields = fields;
                }),
                this.encryptPasswordHistories(model.passwordHistory, key).then((ph) => {
                    cipher.passwordHistory = ph;
                }),
                this.encryptAttachments(model.attachments, key).then((attachments) => {
                    cipher.attachments = attachments;
                }),
            ]);
            return cipher;
        });
    }
    encryptCipherWithCipherKey(model, cipher, keyForCipherKeyEncryption, keyForCipherKeyDecryption) {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            // First, we get the key for cipher key encryption, in its decrypted form
            let decryptedCipherKey;
            if (cipher.key == null) {
                decryptedCipherKey = yield this.keyService.makeCipherKey();
            }
            else {
                decryptedCipherKey = new bw_SymmetricCryptoKey(yield this.encryptService.decryptToBytes(cipher.key, keyForCipherKeyDecryption));
            }
            // Then, we have to encrypt the cipher key with the proper key.
            cipher.key = yield this.encryptService.encrypt(decryptedCipherKey.key, keyForCipherKeyEncryption);
            // Finally, we can encrypt the cipher with the decrypted cipher key.
            return this.encryptCipher(model, cipher, decryptedCipherKey);
        });
    }
    getCipherKeyEncryptionEnabled() {
        return bw_cipher_service_awaiter(this, void 0, void 0, function* () {
            const featureEnabled = yield this.configService.getFeatureFlag(bw_feature_flag_enum_FeatureFlag.CipherKeyEncryption);
            const meetsServerVersion = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.configService.checkServerMeetsVersionRequirement$(bw_CIPHER_KEY_ENC_MIN_SERVER_VER));
            return featureEnabled && meetsServerVersion;
        });
    }
}
bw_cipher_service_decorate([
    bw_sequentialize(() => "getAllDecrypted"),
    bw_cipher_service_metadata("design:type", Function),
    bw_cipher_service_metadata("design:paramtypes", [String]),
    bw_cipher_service_metadata("design:returntype", Promise)
], bw_CipherService.prototype, "getAllDecrypted", null);

;// ../../libs/common/src/vault/services/file-upload/cipher-file-upload.service.ts
var bw_cipher_file_upload_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_CipherFileUploadService {
    constructor(apiService, fileUploadService) {
        this.apiService = apiService;
        this.fileUploadService = fileUploadService;
    }
    upload(cipher, encFileName, encData, admin, dataEncKey) {
        return bw_cipher_file_upload_service_awaiter(this, void 0, void 0, function* () {
            const request = {
                key: dataEncKey[1].encryptedString,
                fileName: encFileName.encryptedString,
                fileSize: encData.buffer.byteLength,
                adminRequest: admin,
            };
            let response;
            try {
                const uploadDataResponse = yield this.apiService.postCipherAttachment(cipher.id, request);
                response = admin ? uploadDataResponse.cipherMiniResponse : uploadDataResponse.cipherResponse;
                yield this.fileUploadService.upload(uploadDataResponse, encFileName, encData, this.generateMethods(uploadDataResponse, response, request.adminRequest));
            }
            catch (e) {
                if ((e instanceof bw_ErrorResponse && e.statusCode === 404) ||
                    e.statusCode === 405) {
                    response = yield this.legacyServerAttachmentFileUpload(request.adminRequest, cipher.id, encFileName, encData, dataEncKey[1]);
                }
                else if (e instanceof bw_ErrorResponse) {
                    throw new Error(e.getSingleMessage());
                }
                else {
                    throw e;
                }
            }
            return response;
        });
    }
    generateMethods(uploadData, response, isAdmin) {
        return {
            postDirect: this.generatePostDirectCallback(uploadData, isAdmin),
            renewFileUploadUrl: this.generateRenewFileUploadUrlCallback(uploadData, response, isAdmin),
            rollback: this.generateRollbackCallback(response, uploadData, isAdmin),
        };
    }
    generatePostDirectCallback(uploadData, isAdmin) {
        return (data) => {
            const response = isAdmin ? uploadData.cipherMiniResponse : uploadData.cipherResponse;
            return this.apiService.postAttachmentFile(response.id, uploadData.attachmentId, data);
        };
    }
    generateRenewFileUploadUrlCallback(uploadData, response, isAdmin) {
        return () => bw_cipher_file_upload_service_awaiter(this, void 0, void 0, function* () {
            const renewResponse = yield this.apiService.renewAttachmentUploadUrl(response.id, uploadData.attachmentId);
            return renewResponse === null || renewResponse === void 0 ? void 0 : renewResponse.url;
        });
    }
    generateRollbackCallback(response, uploadData, isAdmin) {
        return () => {
            if (isAdmin) {
                return this.apiService.deleteCipherAttachmentAdmin(response.id, uploadData.attachmentId);
            }
            else {
                return this.apiService.deleteCipherAttachment(response.id, uploadData.attachmentId);
            }
        };
    }
    /**
     * @deprecated Mar 25 2021: This method has been deprecated in favor of direct uploads.
     * This method still exists for backward compatibility with old server versions.
     */
    legacyServerAttachmentFileUpload(admin, cipherId, encFileName, encData, key) {
        return bw_cipher_file_upload_service_awaiter(this, void 0, void 0, function* () {
            const fd = new FormData();
            try {
                const blob = new Blob([encData.buffer], { type: "application/octet-stream" });
                fd.append("key", key.encryptedString);
                fd.append("data", blob, encFileName.encryptedString);
            }
            catch (e) {
                if (bw_utils_Utils.isNode && !bw_utils_Utils.isBrowser) {
                    fd.append("key", key.encryptedString);
                    fd.append("data", Buffer.from(encData.buffer), {
                        filepath: encFileName.encryptedString,
                        contentType: "application/octet-stream",
                    });
                }
                else {
                    throw e;
                }
            }
            let response;
            try {
                if (admin) {
                    response = yield this.apiService.postCipherAttachmentAdminLegacy(cipherId, fd);
                }
                else {
                    response = yield this.apiService.postCipherAttachmentLegacy(cipherId, fd);
                }
            }
            catch (e) {
                throw new Error(e.getSingleMessage());
            }
            return response;
        });
    }
}

;// ../../libs/common/src/vault/models/request/folder.request.ts
class bw_FolderRequest {
    constructor(folder) {
        this.name = folder.name ? folder.name.encryptedString : null;
    }
}

;// ../../libs/common/src/vault/models/response/folder.response.ts

class bw_folder_response_FolderResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.name = this.getResponseProperty("Name");
        this.revisionDate = this.getResponseProperty("RevisionDate");
    }
}

;// ../../libs/common/src/vault/services/folder/folder-api.service.ts
var bw_folder_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_FolderApiService {
    constructor(folderService, apiService) {
        this.folderService = folderService;
        this.apiService = apiService;
    }
    save(folder, userId) {
        return bw_folder_api_service_awaiter(this, void 0, void 0, function* () {
            const request = new bw_FolderRequest(folder);
            let response;
            if (folder.id == null) {
                response = yield this.postFolder(request);
                folder.id = response.id;
            }
            else {
                response = yield this.putFolder(folder.id, request);
            }
            const data = new bw_FolderData(response);
            yield this.folderService.upsert(data, userId);
            return data;
        });
    }
    delete(id, userId) {
        return bw_folder_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.deleteFolder(id);
            yield this.folderService.delete(id, userId);
        });
    }
    deleteAll(userId) {
        return bw_folder_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.apiService.send("DELETE", "/folders/all", null, true, false);
            yield this.folderService.clear(userId);
        });
    }
    get(id) {
        return bw_folder_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("GET", "/folders/" + id, null, true, true);
            return new bw_folder_response_FolderResponse(r);
        });
    }
    postFolder(request) {
        return bw_folder_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("POST", "/folders", request, true, true);
            return new bw_folder_response_FolderResponse(r);
        });
    }
    putFolder(id, request) {
        return bw_folder_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.apiService.send("PUT", "/folders/" + id, request, true, true);
            return new bw_folder_response_FolderResponse(r);
        });
    }
    deleteFolder(id) {
        return this.apiService.send("DELETE", "/folders/" + id, null, true, false);
    }
}

;// ../../libs/common/src/vault/models/request/folder-with-id.request.ts

class bw_FolderWithIdRequest extends bw_FolderRequest {
    constructor(folder) {
        super(folder);
        this.id = folder.id;
    }
}

;// ../../libs/common/src/vault/services/key-state/folder.state.ts



const bw_FOLDER_ENCRYPTED_FOLDERS = bw_UserKeyDefinition.record(bw_FOLDER_DISK, "folders", {
    deserializer: (obj) => bw_FolderData.fromJSON(obj),
    clearOn: ["logout"],
});
const bw_FOLDER_DECRYPTED_FOLDERS = new bw_UserKeyDefinition(bw_FOLDER_MEMORY, "decryptedFolders", {
    deserializer: (obj) => { var _a; return (_a = obj === null || obj === void 0 ? void 0 : obj.map((f) => bw_FolderView.fromJSON(f))) !== null && _a !== void 0 ? _a : []; },
    clearOn: ["logout", "lock"],
});

;// ../../libs/common/src/vault/services/folder/folder.service.ts
var bw_folder_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







class bw_FolderService {
    constructor(keyService, encryptService, i18nService, cipherService, stateProvider) {
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.i18nService = i18nService;
        this.cipherService = cipherService;
        this.stateProvider = stateProvider;
        /**
         * Ensures we reuse the same observable stream for each userId rather than
         * creating a new one on each folderViews$ call.
         */
        this.folderViewCache = new Map();
        /**
         * Used to force the folderviews$ Observable to re-emit with a provided value.
         * Required because shareReplay with refCount: false maintains last emission.
         * Used during cleanup to force emit empty arrays, ensuring stale data isn't retained.
         */
        this.forceFolderViews = {};
    }
    folders$(userId) {
        return this.encryptedFoldersState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((folders) => {
            if (folders == null) {
                return [];
            }
            return Object.values(folders).map((f) => new bw_Folder(f));
        }));
    }
    /**
     * Returns an Observable of decrypted folder views for the given userId.
     * Uses folderViewCache to maintain a single Observable instance per user,
     * combining normal folder state updates with forced updates.
     */
    folderViews$(userId) {
        if (!this.folderViewCache.has(userId)) {
            if (!this.forceFolderViews[userId]) {
                this.forceFolderViews[userId] = new bw_external_rxjs_namespaceObject.Subject();
            }
            const observable = (0,bw_external_rxjs_namespaceObject.merge)(this.forceFolderViews[userId], this.encryptedFoldersState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.switchMap)((folderData) => {
                return this.decryptFolders(userId, folderData);
            }))).pipe((0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: false, bufferSize: 1 }));
            this.folderViewCache.set(userId, observable);
        }
        return this.folderViewCache.get(userId);
    }
    // TODO: This should be moved to EncryptService or something
    encrypt(model, key) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            const folder = new bw_Folder();
            folder.id = model.id;
            folder.name = yield this.encryptService.encrypt(model.name, key);
            return folder;
        });
    }
    get(id, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            const folders = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.folders$(userId));
            return folders.find((folder) => folder.id === id);
        });
    }
    getDecrypted$(id, userId) {
        return this.folderViews$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((folders) => folders.find((folder) => folder.id === id)), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
    }
    getAllFromState(userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.folders$(userId));
        });
    }
    /**
     * @deprecated For the CLI only
     * @param id id of the folder
     */
    getFromState(id, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            const folder = yield this.get(id, userId);
            if (!folder) {
                return null;
            }
            return folder;
        });
    }
    /**
     * @deprecated Only use in CLI!
     */
    getAllDecryptedFromState(userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.folderViews$(userId));
        });
    }
    upsert(folderData, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            yield this.clearDecryptedFolderState(userId);
            yield this.encryptedFoldersState(userId).update((folders) => {
                if (folders == null) {
                    folders = {};
                }
                if (folderData instanceof bw_FolderData) {
                    const f = folderData;
                    folders[f.id] = f;
                }
                else {
                    folderData.forEach((f) => {
                        folders[f.id] = f;
                    });
                }
                return folders;
            });
        });
    }
    replace(folders, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            if (!folders) {
                return;
            }
            yield this.clearDecryptedFolderState(userId);
            yield this.stateProvider.getUser(userId, bw_FOLDER_ENCRYPTED_FOLDERS).update(() => {
                const newFolders = Object.assign({}, folders);
                return newFolders;
            });
        });
    }
    clearDecryptedFolderState(userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            if (userId == null) {
                throw new Error("User ID is required.");
            }
            yield this.setDecryptedFolders([], userId);
        });
    }
    clear(userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            (_a = this.forceFolderViews[userId]) === null || _a === void 0 ? void 0 : _a.next([]);
            yield this.encryptedFoldersState(userId).update(() => ({}));
            yield this.clearDecryptedFolderState(userId);
        });
    }
    delete(id, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            yield this.clearDecryptedFolderState(userId);
            yield this.encryptedFoldersState(userId).update((folders) => {
                if (folders == null) {
                    return;
                }
                const folderIdsToDelete = Array.isArray(id) ? id : [id];
                folderIdsToDelete.forEach((id) => {
                    if (folders[id] != null) {
                        delete folders[id];
                    }
                });
                return folders;
            });
            // Items in a deleted folder are re-assigned to "No Folder"
            const ciphers = yield this.cipherService.getAll(userId);
            if (ciphers != null) {
                const updates = [];
                for (const cId in ciphers) {
                    if (ciphers[cId].folderId === id) {
                        ciphers[cId].folderId = null;
                        updates.push(ciphers[cId]);
                    }
                }
                if (updates.length > 0) {
                    yield this.cipherService.upsert(updates.map((c) => c.toCipherData()));
                }
            }
        });
    }
    getRotatedData(originalUserKey, newUserKey, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            if (newUserKey == null) {
                throw new Error("New user key is required for rotation.");
            }
            let encryptedFolders = [];
            const folders = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.folderViews$(userId));
            if (!folders) {
                return encryptedFolders;
            }
            encryptedFolders = yield Promise.all(folders.map((folder) => bw_folder_service_awaiter(this, void 0, void 0, function* () {
                const encryptedFolder = yield this.encrypt(folder, newUserKey);
                return new bw_FolderWithIdRequest(encryptedFolder);
            })));
            return encryptedFolders;
        });
    }
    /**
     * Decrypts the folders for a user.
     * @param userId the user id
     * @param folderData encrypted folders
     * @returns a list of decrypted folders
     */
    decryptFolders(userId, folderData) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            // Check if the decrypted folders are already cached
            const decrypted = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.stateProvider.getUser(userId, bw_FOLDER_DECRYPTED_FOLDERS).state$);
            if (decrypted === null || decrypted === void 0 ? void 0 : decrypted.length) {
                return decrypted;
            }
            if (folderData == null) {
                return [];
            }
            const folders = Object.values(folderData).map((f) => new bw_Folder(f));
            const userKey = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.userKey$(userId));
            if (!userKey) {
                return [];
            }
            const decryptFolderPromises = folders.map((f) => f.decryptWithKey(userKey, this.encryptService));
            const decryptedFolders = yield Promise.all(decryptFolderPromises);
            decryptedFolders.sort(bw_utils_Utils.getSortFunction(this.i18nService, "name"));
            const noneFolder = new bw_FolderView();
            noneFolder.name = this.i18nService.t("noneFolder");
            decryptedFolders.push(noneFolder);
            // Cache the decrypted folders
            yield this.setDecryptedFolders(decryptedFolders, userId);
            return decryptedFolders;
        });
    }
    /**
     * @returns a SingleUserState for the encrypted folders.
     */
    encryptedFoldersState(userId) {
        return this.stateProvider.getUser(userId, bw_FOLDER_ENCRYPTED_FOLDERS);
    }
    /**
     * Sets the decrypted folders state for a user.
     * @param folders the decrypted folders
     * @param userId the user id
     */
    setDecryptedFolders(folders, userId) {
        return bw_folder_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_FOLDER_DECRYPTED_FOLDERS, folders, userId);
        });
    }
}

;// ../../libs/common/src/vault/services/totp.service.ts

class bw_TotpService {
    constructor(sdkService) {
        this.sdkService = sdkService;
    }
    getCode$(key) {
        return (0,bw_external_rxjs_namespaceObject.timer)(0, 1000).pipe((0,bw_external_rxjs_namespaceObject.switchMap)(() => this.sdkService.client$.pipe((0,bw_external_rxjs_namespaceObject.map)((sdk) => {
            return sdk.vault().totp().generate_totp(key);
        }))), (0,bw_external_rxjs_namespaceObject.shareReplay)({ refCount: true, bufferSize: 1 }));
    }
}

;// ../../libs/tools/generator/extensions/history/src/generated-password-history.ts
class bw_GeneratedPasswordHistory {
    constructor(password, date) {
        this.password = password;
        this.date = date;
    }
}

;// ../../libs/tools/generator/extensions/history/src/generated-credential.ts
/** A credential generation result */
class bw_src_generated_credential_GeneratedCredential {
    /**
     * Instantiates a generated credential
     * @param credential The value of the generated credential (e.g. a password)
     * @param category The kind of credential
     * @param generationDate The date that the credential was generated.
     *   Numeric values should are interpreted using {@link Date.valueOf}
     *   semantics.
     */
    constructor(credential, category, generationDate) {
        this.credential = credential;
        this.category = category;
        if (typeof generationDate === "number") {
            this.generationDate = new Date(generationDate);
        }
        else {
            this.generationDate = generationDate;
        }
    }
    /** Constructs a credential from its `toJSON` representation */
    static fromJSON(jsonValue) {
        return new bw_src_generated_credential_GeneratedCredential(jsonValue.credential, jsonValue.category, jsonValue.generationDate);
    }
    /** Serializes a credential to a JSON-compatible object */
    toJSON() {
        return {
            credential: this.credential,
            category: this.category,
            generationDate: this.generationDate.valueOf(),
        };
    }
}

;// ../../libs/tools/generator/extensions/history/src/generator-history.abstraction.ts
/** Tracks the history of password generations.
 *  Each user gets their own store.
 */
class bw_GeneratorHistoryService {
}

;// ../../libs/common/src/tools/state/secret-classifier.ts
/** Classifies an object's JSON-serializable data by property into
 *  3 categories:
 *  * Disclosed data MAY be stored in plaintext.
 *  * Excluded data MUST NOT be saved.
 *  * The remaining data is secret and MUST be stored using encryption.
 *
 *  This type should not be used to classify functions.
 *  Data that cannot be serialized by JSON.stringify() should
 *  be excluded.
 */
class bw_SecretClassifier {
    constructor(disclosed, excluded) {
        this.disclosed = disclosed;
        this.excluded = excluded;
    }
    /** Creates a classifier where all properties are secret.
     *  @type {T} The type of secret being classified.
     */
    static allSecret() {
        const disclosed = Object.freeze([]);
        const excluded = Object.freeze([]);
        return new bw_SecretClassifier(disclosed, excluded);
    }
    /** Classify a property as disclosed.
     *  @type {PropertyName} Available secrets to disclose.
     *  @param disclose The property name to disclose.
     *  @returns a new classifier
     */
    disclose(disclose) {
        // update the fluent interface
        const newDisclosed = [...this.disclosed, disclose];
        const classifier = new bw_SecretClassifier(
        // since `NewDisclosed` is opaque to the type checker, it's necessary
        // to assert the type of the array here.
        Object.freeze(newDisclosed), this.excluded);
        return classifier;
    }
    /** Classify a property as excluded.
     *  @type {PropertyName} Available secrets to exclude.
     *  @param exclude The property name to exclude.
     *  @returns a new classifier
     */
    exclude(excludedPropertyName) {
        // update the fluent interface
        const newExcluded = [...this.excluded, excludedPropertyName];
        const classifier = new bw_SecretClassifier(this.disclosed, Object.freeze(newExcluded));
        return classifier;
    }
    /** Partitions `secret` into its disclosed properties and secret properties.
     *  @param value The object to partition
     *  @returns an object that classifies secrets.
     *    The `disclosed` member is new and contains disclosed properties.
     *    The `secret` member is a copy of the secret parameter, including its
     *    prototype, with all disclosed and excluded properties deleted.
     */
    classify(value) {
        // need to JSONify during classification because the prototype is almost guaranteed
        // to be invalid when this  method deletes arbitrary properties.
        const secret = JSON.parse(JSON.stringify(value));
        for (const excludedProp of this.excluded) {
            delete secret[excludedProp];
        }
        const disclosed = {};
        for (const disclosedProp of this.disclosed) {
            // disclosedProp is known to be a subset of the keys of `Plaintext`, so these
            // type assertions are accurate.
            // FIXME: prove it to the compiler
            disclosed[disclosedProp] = secret[disclosedProp];
            delete secret[disclosedProp];
        }
        return {
            disclosed: disclosed,
            secret: secret,
        };
    }
    /** Merges the properties of `secret` and `disclosed`. When `secret` and
     *  `disclosed` contain the same property, the `secret` property overrides
     *  the `disclosed` property.
     *  @param disclosed an object whose disclosed properties are merged into
     *    the output. Unknown properties are ignored.
     *  @param secret an objects whose properties are merged into the output.
     *    Excluded properties are ignored. Unknown properties are retained.
     *  @returns a new object containing the merged data.
     */
    // Declassified data is always jsonified--the purpose of classifying it is to Jsonify it,
    // which causes type conversions.
    declassify(disclosed, secret) {
        // removed unknown keys from `disclosed` to prevent any old edit
        // of plaintext data from being laundered though declassification.
        const cleaned = {};
        for (const disclosedProp of this.disclosed) {
            cleaned[disclosedProp] = disclosed[disclosedProp];
        }
        // merge decrypted into cleaned so that secret data clobbers public data
        const merged = Object.assign(cleaned, secret);
        // delete excluded props
        for (const excludedProp of this.excluded) {
            delete merged[excludedProp];
        }
        return merged;
    }
}

;// ../../libs/tools/generator/extensions/history/src/key-definitions.ts
var bw_key_definitions_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};






/** encrypted password generation history */
const bw_GENERATOR_HISTORY = bw_SecretKeyDefinition.array(bw_GENERATOR_DISK, "localGeneratorHistory", bw_SecretClassifier.allSecret(), {
    deserializer: bw_src_generated_credential_GeneratedCredential.fromJSON,
    clearOn: ["logout"],
});
/** encrypted password generation history subject to migration */
const bw_GENERATOR_HISTORY_BUFFER = new bw_BufferedKeyDefinition(bw_GENERATOR_DISK, "localGeneratorHistoryBuffer", {
    deserializer(history) {
        const items = history;
        return items === null || items === void 0 ? void 0 : items.map((h) => new bw_GeneratedPasswordHistory(h.password, h.date));
    },
    isValid(history) {
        return bw_key_definitions_awaiter(this, void 0, void 0, function* () {
            return history.length ? true : false;
        });
    },
    map(history, decryptor) {
        return bw_key_definitions_awaiter(this, void 0, void 0, function* () {
            const credentials = yield decryptor.decrypt(history);
            const mapped = credentials.map((c) => new bw_src_generated_credential_GeneratedCredential(c.password, "password", c.date));
            return mapped;
        });
    },
    clearOn: ["logout"],
});

;// ../../libs/tools/generator/extensions/history/src/legacy-password-history-decryptor.ts
var bw_legacy_password_history_decryptor_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


/** Strategy that decrypts a password history */
class bw_LegacyPasswordHistoryDecryptor {
    constructor(userId, keyService, encryptService) {
        this.userId = userId;
        this.keyService = keyService;
        this.encryptService = encryptService;
    }
    /** Decrypts a password history. */
    decrypt(history) {
        return bw_legacy_password_history_decryptor_awaiter(this, void 0, void 0, function* () {
            const key = yield this.keyService.getUserKey(this.userId);
            const promises = (history !== null && history !== void 0 ? history : []).map((item) => bw_legacy_password_history_decryptor_awaiter(this, void 0, void 0, function* () {
                const encrypted = new bw_enc_string_EncString(item.password);
                const decrypted = yield this.encryptService.decryptToUtf8(encrypted, key);
                return new bw_GeneratedPasswordHistory(decrypted, item.date);
            }));
            const decrypted = yield Promise.all(promises);
            return decrypted;
        });
    }
}

;// ../../libs/tools/generator/extensions/history/src/local-generator-history.service.ts
var bw_local_generator_history_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore









const bw_local_generator_history_service_OPTIONS_FRAME_SIZE = 2048;
/** Tracks the history of password generations local to a device.
 *  {@link GeneratorHistoryService}
 */
class bw_LocalGeneratorHistoryService extends bw_GeneratorHistoryService {
    constructor(encryptService, keyService, stateProvider, options = { maxTotal: 200 }) {
        super();
        this.encryptService = encryptService;
        this.keyService = keyService;
        this.stateProvider = stateProvider;
        this.options = options;
        this._credentialStates = new Map();
        /** {@link GeneratorHistoryService.track} */
        this.track = (userId, credential, category, date) => bw_local_generator_history_service_awaiter(this, void 0, void 0, function* () {
            const state = this.getCredentialState(userId);
            let result = null;
            yield state.update((credentials) => {
                credentials = credentials !== null && credentials !== void 0 ? credentials : [];
                // add the result
                result = new bw_src_generated_credential_GeneratedCredential(credential, category, date !== null && date !== void 0 ? date : Date.now());
                credentials.unshift(result);
                // trim history
                const removeAt = Math.max(0, this.options.maxTotal);
                credentials.splice(removeAt, Infinity);
                return credentials;
            }, {
                shouldUpdate: (credentials) => { var _a; return !((_a = credentials === null || credentials === void 0 ? void 0 : credentials.some((f) => f.credential === credential)) !== null && _a !== void 0 ? _a : false); },
            });
            return result;
        });
        /** {@link GeneratorHistoryService.take} */
        this.take = (userId, credential) => bw_local_generator_history_service_awaiter(this, void 0, void 0, function* () {
            const state = this.getCredentialState(userId);
            let credentialIndex;
            let result = null;
            yield state.update((credentials) => {
                credentials = credentials !== null && credentials !== void 0 ? credentials : [];
                [result] = credentials.splice(credentialIndex, 1);
                return credentials;
            }, {
                shouldUpdate: (credentials) => {
                    var _a;
                    credentialIndex = (_a = credentials === null || credentials === void 0 ? void 0 : credentials.findIndex((f) => f.credential === credential)) !== null && _a !== void 0 ? _a : -1;
                    return credentialIndex >= 0;
                },
            });
            return result;
        });
        /** {@link GeneratorHistoryService.take} */
        this.clear = (userId) => bw_local_generator_history_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const state = this.getCredentialState(userId);
            const result = (_a = (yield state.update(() => null))) !== null && _a !== void 0 ? _a : [];
            return result;
        });
        /** {@link GeneratorHistoryService.credentials$} */
        this.credentials$ = (userId) => {
            return this.getCredentialState(userId).state$.pipe((0,bw_external_rxjs_namespaceObject.map)((credentials) => credentials !== null && credentials !== void 0 ? credentials : []));
        };
    }
    getCredentialState(userId) {
        let state = this._credentialStates.get(userId);
        if (!state) {
            state = this.createSecretState(userId);
            this._credentialStates.set(userId, state);
        }
        return state;
    }
    createSecretState(userId) {
        // construct the encryptor
        const packer = new bw_PaddedDataPacker(bw_local_generator_history_service_OPTIONS_FRAME_SIZE);
        const encryptor$ = this.keyService.userKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((key) => (key ? new bw_UserKeyEncryptor(userId, this.encryptService, key, packer) : null)), (0,bw_external_rxjs_namespaceObject.filter)((encryptor) => !!encryptor));
        // construct the durable state
        const state = bw_SecretState.from(userId, bw_GENERATOR_HISTORY, this.stateProvider, encryptor$);
        // decryptor is just an algorithm, but it can't run until the key is available;
        // providing it via an observable makes running it early impossible
        const decryptor = new bw_LegacyPasswordHistoryDecryptor(userId, this.keyService, this.encryptService);
        const decryptor$ = this.keyService.userKey$(userId).pipe((0,bw_external_rxjs_namespaceObject.map)((key) => key && decryptor));
        // move data from the old password history once decryptor is available
        const buffer = new bw_BufferedState(this.stateProvider, bw_GENERATOR_HISTORY_BUFFER, state, decryptor$);
        return buffer;
    }
}

;// ../../libs/tools/generator/extensions/history/src/index.ts





;// ../../libs/tools/generator/extensions/navigation/src/default-generator-navigation.ts
/** The default options for password generation. */
const bw_DefaultGeneratorNavigation = Object.freeze({
    type: "password",
    username: "word",
    forwarder: "",
});

;// ../../libs/tools/generator/extensions/navigation/src/generator-navigation-evaluator.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/** Enforces policy for generator navigation options.
 */
class bw_GeneratorNavigationEvaluator {
    /** Instantiates the evaluator.
     * @param policy The policy applied by the evaluator. When this conflicts with
     *               the defaults, the policy takes precedence.
     */
    constructor(policy) {
        this.policy = policy;
    }
    /** {@link PolicyEvaluator.policyInEffect} */
    get policyInEffect() {
        var _a;
        return bw_generator_types_PasswordAlgorithms.includes((_a = this.policy) === null || _a === void 0 ? void 0 : _a.overridePasswordType);
    }
    /** Apply policy to the input options.
     *  @param options The options to build from. These options are not altered.
     *  @returns A new password generation request with policy applied.
     */
    applyPolicy(options) {
        var _a;
        const result = Object.assign({}, options);
        if (this.policyInEffect) {
            result.type = (_a = this.policy.overridePasswordType) !== null && _a !== void 0 ? _a : result.type;
        }
        return result;
    }
    /** Ensures internal options consistency.
     *  @param options The options to cascade. These options are not altered.
     *  @returns A passphrase generation request with cascade applied.
     */
    sanitize(options) {
        var _a;
        return Object.assign(Object.assign({}, options), { type: (_a = options.type) !== null && _a !== void 0 ? _a : bw_DefaultGeneratorNavigation.type });
    }
}

;// ../../libs/tools/generator/extensions/navigation/src/generator-navigation-policy.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore

/** Reduces a policy into an accumulator by preferring the password generator
 *  type to other generator types.
 *  @param acc the accumulator
 *  @param policy the policy to reduce
 *  @returns the resulting `GeneratorNavigationPolicy`
 */
function bw_preferPassword(acc, policy) {
    const isEnabled = policy.type === bw_policy_type_enum_PolicyType.PasswordGenerator && policy.enabled;
    if (!isEnabled) {
        return acc;
    }
    const isOverridable = acc.overridePasswordType !== "password" && policy.data.overridePasswordType;
    const result = isOverridable
        ? Object.assign(Object.assign({}, acc), { overridePasswordType: policy.data.overridePasswordType }) : acc;
    return result;
}
/** The default options for password generation policy. */
const bw_DisabledGeneratorNavigationPolicy = Object.freeze({
    overridePasswordType: null,
});

;// ../../libs/tools/generator/extensions/navigation/src/key-definitions.ts

/** plaintext password generation options */
const bw_GENERATOR_SETTINGS = new bw_UserKeyDefinition(bw_GENERATOR_DISK, "generatorSettings", {
    deserializer: (value) => value,
    clearOn: ["logout"],
});

;// ../../libs/tools/generator/extensions/navigation/src/default-generator-navigation.service.ts
var bw_default_generator_navigation_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};







class bw_default_generator_navigation_service_DefaultGeneratorNavigationService {
    /** instantiates the password generator strategy.
     * @param stateProvider provides durable state
     * @param policy provides the policy to enforce
     */
    constructor(stateProvider, policy) {
        this.stateProvider = stateProvider;
        this.policy = policy;
    }
    /** An observable monitoring the options saved to disk.
     *  The observable updates when the options are saved.
     *   @param userId: Identifies the user making the request
     */
    options$(userId) {
        return this.stateProvider.getUserState$(bw_GENERATOR_SETTINGS, userId);
    }
    /** Gets the default options. */
    defaults$(userId) {
        return new bw_external_rxjs_namespaceObject.BehaviorSubject(Object.assign({}, bw_DefaultGeneratorNavigation));
    }
    /** An observable monitoring the options used to enforce policy.
     *  The observable updates when the policy changes.
     *  @param userId: Identifies the user making the request
     */
    evaluator$(userId) {
        const evaluator$ = this.policy.getAll$(bw_policy_type_enum_PolicyType.PasswordGenerator, userId).pipe(bw_rx_reduceCollection(bw_preferPassword, bw_DisabledGeneratorNavigationPolicy), bw_rx_distinctIfShallowMatch(), (0,bw_external_rxjs_namespaceObject.map)((policy) => new bw_GeneratorNavigationEvaluator(policy)));
        return evaluator$;
    }
    /** Enforces the policy on the given options
     * @param userId: Identifies the user making the request
     * @param options the options to enforce the policy on
     * @returns a new instance of the options with the policy enforced
     */
    enforcePolicy(userId, options) {
        return bw_default_generator_navigation_service_awaiter(this, void 0, void 0, function* () {
            const evaluator = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.evaluator$(userId));
            const applied = evaluator.applyPolicy(options);
            const sanitized = evaluator.sanitize(applied);
            return sanitized;
        });
    }
    /** Saves the navigation options to disk.
     * @param userId: Identifies the user making the request
     * @param options the options to save
     * @returns a promise that resolves when the options are saved
     */
    saveOptions(userId, options) {
        return bw_default_generator_navigation_service_awaiter(this, void 0, void 0, function* () {
            yield this.stateProvider.setUserState(bw_GENERATOR_SETTINGS, options, userId);
        });
    }
}

;// ../../libs/tools/generator/extensions/navigation/src/index.ts





;// ../../libs/common/src/admin-console/models/domain/password-generator-policy-options.ts

/** Enterprise policy for the password generator.
 * @see PolicyType.PasswordGenerator
 */
class bw_PasswordGeneratorPolicyOptions extends bw_domain_base_Domain {
    constructor() {
        super(...arguments);
        /** The default kind of credential to generate */
        this.overridePasswordType = "";
        /** The minimum length of generated passwords.
         *  When this is less than or equal to zero, it is ignored.
         *  If this is less than the total number of characters required by
         *  the policy's other settings, then it is ignored.
         *  This field is not used for passphrases.
         */
        this.minLength = 0;
        /** When this is true, an uppercase character must be part of
         *  the generated password.
         *  This field is not used for passphrases.
         */
        this.useUppercase = false;
        /** When this is true, a lowercase character must be part of
         *  the generated password. This field is not used for passphrases.
         */
        this.useLowercase = false;
        /** When this is true, at least one digit must be part of the generated
         *  password. This field is not used for passphrases.
         */
        this.useNumbers = false;
        /** The quantity of digits to include in the generated password.
         *  When this is less than or equal to zero, it is ignored.
         *  This field is not used for passphrases.
         */
        this.numberCount = 0;
        /** When this is true, at least one digit must be part of the generated
         *  password. This field is not used for passphrases.
         */
        this.useSpecial = false;
        /** The quantity of special characters to include in the generated
         *  password. When this is less than or equal to zero, it is ignored.
         *  This field is not used for passphrases.
         */
        this.specialCount = 0;
        /** The minimum number of words required by generated passphrases.
         *  This field is not used for passwords.
         */
        this.minNumberWords = 0;
        /** When this is true, the first letter of each word in the passphrase
         *  is capitalized. This field is not used for passwords.
         */
        this.capitalize = false;
        /** When this is true, a number is included within the passphrase.
         *  This field is not used for passwords.
         */
        this.includeNumber = false;
    }
    /** Checks whether the policy affects the password generator.
     * @returns True if at least one password or passphrase requirement has been set.
     * If it returns False, then no requirements have been set and the policy should
     * not be enforced.
     */
    inEffect() {
        return (this.overridePasswordType ||
            this.minLength > 0 ||
            this.numberCount > 0 ||
            this.specialCount > 0 ||
            this.useUppercase ||
            this.useLowercase ||
            this.useNumbers ||
            this.useSpecial ||
            this.minNumberWords > 0 ||
            this.capitalize ||
            this.includeNumber);
    }
    /** Creates a copy of the policy.
     */
    clone() {
        const policy = new bw_PasswordGeneratorPolicyOptions();
        Object.assign(policy, this);
        return policy;
    }
}

;// ../../libs/tools/generator/extensions/legacy/src/legacy-password-generation.service.ts
var bw_legacy_password_generation_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



/** Adapts the generator 2.0 design to 1.0 angular services. */
class bw_LegacyPasswordGenerationService {
    constructor(accountService, navigation, passwords, passphrases, history) {
        this.accountService = accountService;
        this.navigation = navigation;
        this.passwords = passwords;
        this.passphrases = passphrases;
        this.history = history;
    }
    generatePassword(options) {
        if (options.type === "password") {
            return this.passwords.generate(options);
        }
        else {
            return this.passphrases.generate(options);
        }
    }
    generatePassphrase(options) {
        return this.passphrases.generate(options);
    }
    getRawOptions$() {
        function withSequenceNumber(observable$) {
            return observable$.pipe((0,bw_external_rxjs_namespaceObject.map)((evaluator, i) => [evaluator, i]));
        }
        // initial array ensures that destructuring never fails; sequence numbers
        // set to `-1` so that the first update reflects that the policy changed from
        // "unknown" to "whatever was provided by the service". This needs to be called
        // each time the active user changes or the `concat` will block.
        function initial$() {
            const initial = [
                null,
                null,
                [null, -1],
                null,
                null,
                [null, -1],
                null,
                null,
                [null, -1],
            ];
            return (0,bw_external_rxjs_namespaceObject.of)(initial);
        }
        function intermediatePairsToRawOptions([previous, current]) {
            const [, , [, passwordPrevious], , , [, passphrasePrevious], , , [, generatorPrevious]] = previous;
            const [passwordOptions, passwordDefaults, [passwordEvaluator, passwordCurrent], passphraseOptions, passphraseDefaults, [passphraseEvaluator, passphraseCurrent], generatorOptions, generatorDefaults, [generatorEvaluator, generatorCurrent],] = current;
            // when any of the sequence numbers change, the emission occurs as the result of
            // a policy update
            const policyEmitted = passwordPrevious < passwordCurrent ||
                passphrasePrevious < passphraseCurrent ||
                generatorPrevious < generatorCurrent;
            const result = [
                passwordOptions,
                passwordDefaults,
                passwordEvaluator,
                passphraseOptions,
                passphraseDefaults,
                passphraseEvaluator,
                generatorOptions,
                generatorDefaults,
                generatorEvaluator,
                policyEmitted,
            ];
            return result;
        }
        // look upon my works, ye mighty, and despair!
        const rawOptions$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)((activeUser) => (0,bw_external_rxjs_namespaceObject.concat)(initial$(), (0,bw_external_rxjs_namespaceObject.combineLatest)([
            this.passwords.options$(activeUser.id),
            this.passwords.defaults$(activeUser.id),
            withSequenceNumber(this.passwords.evaluator$(activeUser.id)),
            this.passphrases.options$(activeUser.id),
            this.passphrases.defaults$(activeUser.id),
            withSequenceNumber(this.passphrases.evaluator$(activeUser.id)),
            this.navigation.options$(activeUser.id),
            this.navigation.defaults$(activeUser.id),
            withSequenceNumber(this.navigation.evaluator$(activeUser.id)),
        ]))), (0,bw_external_rxjs_namespaceObject.pairwise)(), (0,bw_external_rxjs_namespaceObject.map)(intermediatePairsToRawOptions));
        return rawOptions$;
    }
    getOptions$() {
        const options$ = this.getRawOptions$().pipe((0,bw_external_rxjs_namespaceObject.map)(([passwordOptions, passwordDefaults, passwordEvaluator, passphraseOptions, passphraseDefaults, passphraseEvaluator, generatorOptions, generatorDefaults, generatorEvaluator, policyUpdated,]) => {
            const passwordOptionsWithPolicy = passwordEvaluator.applyPolicy(passwordOptions !== null && passwordOptions !== void 0 ? passwordOptions : passwordDefaults);
            const passphraseOptionsWithPolicy = passphraseEvaluator.applyPolicy(passphraseOptions !== null && passphraseOptions !== void 0 ? passphraseOptions : passphraseDefaults);
            const generatorOptionsWithPolicy = generatorEvaluator.applyPolicy(generatorOptions !== null && generatorOptions !== void 0 ? generatorOptions : generatorDefaults);
            const options = this.toPasswordGeneratorOptions({
                password: passwordEvaluator.sanitize(passwordOptionsWithPolicy),
                passphrase: passphraseEvaluator.sanitize(passphraseOptionsWithPolicy),
                generator: generatorEvaluator.sanitize(generatorOptionsWithPolicy),
                policyUpdated,
            });
            const policy = Object.assign(new bw_PasswordGeneratorPolicyOptions(), passwordEvaluator.policy, passphraseEvaluator.policy, generatorEvaluator.policy);
            return [options, policy];
        }));
        return options$;
    }
    getOptions() {
        return bw_legacy_password_generation_service_awaiter(this, void 0, void 0, function* () {
            return yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.getOptions$());
        });
    }
    enforcePasswordGeneratorPoliciesOnOptions(options) {
        return bw_legacy_password_generation_service_awaiter(this, void 0, void 0, function* () {
            const options$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)((activeUser) => (0,bw_external_rxjs_namespaceObject.zip)(this.passwords.evaluator$(activeUser.id), this.passphrases.evaluator$(activeUser.id), this.navigation.evaluator$(activeUser.id))), (0,bw_external_rxjs_namespaceObject.map)(([passwordEvaluator, passphraseEvaluator, navigationEvaluator]) => {
                const policy = Object.assign(new bw_PasswordGeneratorPolicyOptions(), passwordEvaluator.policy, passphraseEvaluator.policy, navigationEvaluator.policy);
                const navigationApplied = navigationEvaluator.applyPolicy(options);
                const navigationSanitized = Object.assign(Object.assign({}, options), navigationEvaluator.sanitize(navigationApplied));
                if (navigationSanitized.type === "password") {
                    const applied = passwordEvaluator.applyPolicy(navigationSanitized);
                    const sanitized = passwordEvaluator.sanitize(applied);
                    return [sanitized, policy];
                }
                else {
                    const applied = passphraseEvaluator.applyPolicy(navigationSanitized);
                    const sanitized = passphraseEvaluator.sanitize(applied);
                    return [sanitized, policy];
                }
            }));
            const [sanitized, policy] = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(options$);
            return [
                // callers assume this function updates the options parameter
                Object.assign(options, sanitized),
                policy,
            ];
        });
    }
    saveOptions(options) {
        return bw_legacy_password_generation_service_awaiter(this, void 0, void 0, function* () {
            const stored = this.toStoredOptions(options);
            const activeAccount = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            // generator settings needs to preserve whether password or passphrase is selected,
            // so `navigationOptions` is mutated.
            const navigationOptions$ = (0,bw_external_rxjs_namespaceObject.zip)(this.navigation.options$(activeAccount.id), this.navigation.defaults$(activeAccount.id)).pipe((0,bw_external_rxjs_namespaceObject.map)(([options, defaults]) => options !== null && options !== void 0 ? options : defaults));
            let navigationOptions = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(navigationOptions$);
            navigationOptions = Object.assign(navigationOptions, stored.generator);
            yield this.navigation.saveOptions(activeAccount.id, navigationOptions);
            // overwrite all other settings with latest values
            yield this.passwords.saveOptions(activeAccount.id, stored.password);
            yield this.passphrases.saveOptions(activeAccount.id, stored.passphrase);
        });
    }
    toStoredOptions(options) {
        return {
            generator: {
                type: options.type,
            },
            password: {
                length: options.length,
                minLength: options.minLength,
                ambiguous: options.ambiguous,
                uppercase: options.uppercase,
                minUppercase: options.minUppercase,
                lowercase: options.lowercase,
                minLowercase: options.minLowercase,
                number: options.number,
                minNumber: options.minNumber,
                special: options.special,
                minSpecial: options.minSpecial,
            },
            passphrase: {
                numWords: options.numWords,
                wordSeparator: options.wordSeparator,
                capitalize: options.capitalize,
                includeNumber: options.includeNumber,
            },
            policyUpdated: false,
        };
    }
    toPasswordGeneratorOptions(options) {
        return {
            type: options.generator.type,
            length: options.password.length,
            minLength: options.password.minLength,
            ambiguous: options.password.ambiguous,
            uppercase: options.password.uppercase,
            minUppercase: options.password.minUppercase,
            lowercase: options.password.lowercase,
            minLowercase: options.password.minLowercase,
            number: options.password.number,
            minNumber: options.password.minNumber,
            special: options.password.special,
            minSpecial: options.password.minSpecial,
            numWords: options.passphrase.numWords,
            wordSeparator: options.passphrase.wordSeparator,
            capitalize: options.passphrase.capitalize,
            includeNumber: options.passphrase.includeNumber,
            policyUpdated: options.policyUpdated,
        };
    }
    getHistory() {
        const history = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.concatMap)((account) => this.history.credentials$(account.id)), (0,bw_external_rxjs_namespaceObject.timeout)({
            // timeout after 1 second
            each: 1000,
            with() {
                return [];
            },
        }), (0,bw_external_rxjs_namespaceObject.map)((history) => history.map(bw_toGeneratedPasswordHistory)));
        return (0,bw_external_rxjs_namespaceObject.firstValueFrom)(history);
    }
    addHistory(password) {
        return bw_legacy_password_generation_service_awaiter(this, void 0, void 0, function* () {
            const account = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            if (account === null || account === void 0 ? void 0 : account.id) {
                // legacy service doesn't distinguish credential types
                yield this.history.track(account.id, password, "password");
            }
        });
    }
    clear() {
        const history$ = this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.filter)((account) => !!(account === null || account === void 0 ? void 0 : account.id)), (0,bw_external_rxjs_namespaceObject.concatMap)((account) => this.history.clear(account.id)), (0,bw_external_rxjs_namespaceObject.timeout)({
            // timeout after 1 second
            each: 1000,
            with() {
                return [];
            },
        }), (0,bw_external_rxjs_namespaceObject.map)((history) => history.map(bw_toGeneratedPasswordHistory)));
        return (0,bw_external_rxjs_namespaceObject.firstValueFrom)(history$);
    }
}
function bw_toGeneratedPasswordHistory(value) {
    return new bw_GeneratedPasswordHistory(value.credential, value.generationDate.valueOf());
}

;// ../../libs/tools/generator/extensions/legacy/src/create-legacy-password-generation-service.ts




const { /* PassphraseGeneratorStrategy */ "jK": bw_create_legacy_password_generation_service_PassphraseGeneratorStrategy, /* PasswordGeneratorStrategy */ "gb": bw_create_legacy_password_generation_service_PasswordGeneratorStrategy } = bw_strategies_namespaceObject;
const { /* KeyServiceRandomizer */ "q4": bw_create_legacy_password_generation_service_KeyServiceRandomizer, /* PasswordRandomizer */ "Zx": bw_create_legacy_password_generation_service_PasswordRandomizer } = bw_engine_namespaceObject;
const bw_create_legacy_password_generation_service_DefaultGeneratorService = bw_DefaultGeneratorService;
function bw_legacyPasswordGenerationServiceFactory(encryptService, keyService, policyService, accountService, stateProvider) {
    const randomizer = new bw_create_legacy_password_generation_service_KeyServiceRandomizer(keyService);
    const passwordRandomizer = new bw_create_legacy_password_generation_service_PasswordRandomizer(randomizer);
    const passwords = new bw_create_legacy_password_generation_service_DefaultGeneratorService(new bw_create_legacy_password_generation_service_PasswordGeneratorStrategy(passwordRandomizer, stateProvider), policyService);
    const passphrases = new bw_create_legacy_password_generation_service_DefaultGeneratorService(new bw_create_legacy_password_generation_service_PassphraseGeneratorStrategy(passwordRandomizer, stateProvider), policyService);
    const navigation = new bw_default_generator_navigation_service_DefaultGeneratorNavigationService(stateProvider, policyService);
    const history = new bw_LocalGeneratorHistoryService(encryptService, keyService, stateProvider);
    return new bw_LegacyPasswordGenerationService(accountService, navigation, passwords, passphrases, history);
}

;// ../../libs/tools/generator/extensions/legacy/src/legacy-username-generation.service.ts
var bw_legacy_username_generation_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/** Adapts the generator 2.0 design to 1.0 angular services. */
class bw_legacy_username_generation_service_LegacyUsernameGenerationService {
    constructor(accountService, navigation, catchall, effUsername, subaddress, addyIo, duckDuckGo, fastmail, firefoxRelay, forwardEmail, simpleLogin) {
        this.accountService = accountService;
        this.navigation = navigation;
        this.catchall = catchall;
        this.effUsername = effUsername;
        this.subaddress = subaddress;
        this.addyIo = addyIo;
        this.duckDuckGo = duckDuckGo;
        this.fastmail = fastmail;
        this.firefoxRelay = firefoxRelay;
        this.forwardEmail = forwardEmail;
        this.simpleLogin = simpleLogin;
    }
    generateUsername(options) {
        if (options.type === "catchall") {
            return this.generateCatchall(options);
        }
        else if (options.type === "subaddress") {
            return this.generateSubaddress(options);
        }
        else if (options.type === "forwarded") {
            return this.generateForwarded(options);
        }
        else {
            return this.generateWord(options);
        }
    }
    generateWord(options) {
        return this.effUsername.generate(options);
    }
    generateSubaddress(options) {
        return this.subaddress.generate(options);
    }
    generateCatchall(options) {
        return this.catchall.generate(options);
    }
    generateForwarded(options) {
        if (!options.forwardedService) {
            return null;
        }
        const stored = this.toStoredOptions(options);
        switch (options.forwardedService) {
            case Forwarders.AddyIo.id:
                return this.addyIo.generate(stored.forwarders.addyIo);
            case Forwarders.DuckDuckGo.id:
                return this.duckDuckGo.generate(stored.forwarders.duckDuckGo);
            case Forwarders.Fastmail.id:
                return this.fastmail.generate(stored.forwarders.fastmail);
            case Forwarders.FirefoxRelay.id:
                return this.firefoxRelay.generate(stored.forwarders.firefoxRelay);
            case Forwarders.ForwardEmail.id:
                return this.forwardEmail.generate(stored.forwarders.forwardEmail);
            case Forwarders.SimpleLogin.id:
                return this.simpleLogin.generate(stored.forwarders.simpleLogin);
        }
    }
    getOptions$() {
        // look upon my works, ye mighty, and despair!
        const options$ = this.accountService.activeAccount$.pipe(concatMap((account) => combineLatest([
            this.navigation.options$(account.id),
            this.navigation.defaults$(account.id),
            this.catchall.options$(account.id),
            this.catchall.defaults$(account.id),
            this.effUsername.options$(account.id),
            this.effUsername.defaults$(account.id),
            this.subaddress.options$(account.id),
            this.subaddress.defaults$(account.id),
            this.addyIo.options$(account.id),
            this.addyIo.defaults$(account.id),
            this.duckDuckGo.options$(account.id),
            this.duckDuckGo.defaults$(account.id),
            this.fastmail.options$(account.id),
            this.fastmail.defaults$(account.id),
            this.firefoxRelay.options$(account.id),
            this.firefoxRelay.defaults$(account.id),
            this.forwardEmail.options$(account.id),
            this.forwardEmail.defaults$(account.id),
            this.simpleLogin.options$(account.id),
            this.simpleLogin.defaults$(account.id),
        ])), map(([generatorOptions, generatorDefaults, catchallOptions, catchallDefaults, effUsernameOptions, effUsernameDefaults, subaddressOptions, subaddressDefaults, addyIoOptions, addyIoDefaults, duckDuckGoOptions, duckDuckGoDefaults, fastmailOptions, fastmailDefaults, firefoxRelayOptions, firefoxRelayDefaults, forwardEmailOptions, forwardEmailDefaults, simpleLoginOptions, simpleLoginDefaults,]) => this.toUsernameOptions({
            generator: generatorOptions !== null && generatorOptions !== void 0 ? generatorOptions : generatorDefaults,
            algorithms: {
                catchall: catchallOptions !== null && catchallOptions !== void 0 ? catchallOptions : catchallDefaults,
                effUsername: effUsernameOptions !== null && effUsernameOptions !== void 0 ? effUsernameOptions : effUsernameDefaults,
                subaddress: subaddressOptions !== null && subaddressOptions !== void 0 ? subaddressOptions : subaddressDefaults,
            },
            forwarders: {
                addyIo: addyIoOptions !== null && addyIoOptions !== void 0 ? addyIoOptions : addyIoDefaults,
                duckDuckGo: duckDuckGoOptions !== null && duckDuckGoOptions !== void 0 ? duckDuckGoOptions : duckDuckGoDefaults,
                fastmail: fastmailOptions !== null && fastmailOptions !== void 0 ? fastmailOptions : fastmailDefaults,
                firefoxRelay: firefoxRelayOptions !== null && firefoxRelayOptions !== void 0 ? firefoxRelayOptions : firefoxRelayDefaults,
                forwardEmail: forwardEmailOptions !== null && forwardEmailOptions !== void 0 ? forwardEmailOptions : forwardEmailDefaults,
                simpleLogin: simpleLoginOptions !== null && simpleLoginOptions !== void 0 ? simpleLoginOptions : simpleLoginDefaults,
            },
        })));
        return options$;
    }
    getOptions() {
        return firstValueFrom(this.getOptions$());
    }
    saveOptions(options) {
        return bw_legacy_username_generation_service_awaiter(this, void 0, void 0, function* () {
            const stored = this.toStoredOptions(options);
            const activeAccount = yield firstValueFrom(this.accountService.activeAccount$);
            const saved = yield this.saveGeneratorOptions(activeAccount.id, options.type, stored);
            if (!saved) {
                yield this.saveForwarderOptions(activeAccount.id, options.forwardedService, stored);
            }
            // run navigation options 2nd so that navigation options update doesn't race the `saved options`
            // update in Firefox.
            yield this.saveNavigationOptions(activeAccount.id, stored);
        });
    }
    saveNavigationOptions(account, options) {
        return bw_legacy_username_generation_service_awaiter(this, void 0, void 0, function* () {
            // generator settings needs to preserve whether password or passphrase is selected,
            // so `navigationOptions` is mutated.
            const navigationOptions$ = zip(this.navigation.options$(account), this.navigation.defaults$(account)).pipe(map(([options, defaults]) => options !== null && options !== void 0 ? options : defaults));
            let navigationOptions = yield firstValueFrom(navigationOptions$);
            navigationOptions = Object.assign(navigationOptions, options.generator);
            yield this.navigation.saveOptions(account, navigationOptions);
        });
    }
    saveGeneratorOptions(account, type, options) {
        return bw_legacy_username_generation_service_awaiter(this, void 0, void 0, function* () {
            switch (type) {
                case "word":
                    yield this.effUsername.saveOptions(account, options.algorithms.effUsername);
                    return true;
                case "subaddress":
                    yield this.subaddress.saveOptions(account, options.algorithms.subaddress);
                    return true;
                case "catchall":
                    yield this.catchall.saveOptions(account, options.algorithms.catchall);
                    return true;
                default:
                    return false;
            }
        });
    }
    saveForwarderOptions(account, forwarder, options) {
        return bw_legacy_username_generation_service_awaiter(this, void 0, void 0, function* () {
            switch (forwarder) {
                case "anonaddy":
                    yield this.addyIo.saveOptions(account, options.forwarders.addyIo);
                    return true;
                case "duckduckgo":
                    yield this.duckDuckGo.saveOptions(account, options.forwarders.duckDuckGo);
                    return true;
                case "fastmail":
                    yield this.fastmail.saveOptions(account, options.forwarders.fastmail);
                    return true;
                case "firefoxrelay":
                    yield this.firefoxRelay.saveOptions(account, options.forwarders.firefoxRelay);
                    return true;
                case "forwardemail":
                    yield this.forwardEmail.saveOptions(account, options.forwarders.forwardEmail);
                    return true;
                case "simplelogin":
                    yield this.simpleLogin.saveOptions(account, options.forwarders.simpleLogin);
                    return true;
                default:
                    return false;
            }
        });
    }
    toStoredOptions(options) {
        const forwarders = {
            addyIo: {
                baseUrl: options.forwardedAnonAddyBaseUrl,
                token: options.forwardedAnonAddyApiToken,
                domain: options.forwardedAnonAddyDomain,
                website: options.website,
            },
            duckDuckGo: {
                token: options.forwardedDuckDuckGoToken,
                website: options.website,
            },
            fastmail: {
                token: options.forwardedFastmailApiToken,
                website: options.website,
            },
            firefoxRelay: {
                token: options.forwardedFirefoxApiToken,
                website: options.website,
            },
            forwardEmail: {
                token: options.forwardedForwardEmailApiToken,
                domain: options.forwardedForwardEmailDomain,
                website: options.website,
            },
            simpleLogin: {
                token: options.forwardedSimpleLoginApiKey,
                baseUrl: options.forwardedSimpleLoginBaseUrl,
                website: options.website,
            },
        };
        const generator = {
            username: options.type,
            forwarder: options.forwardedService,
        };
        const algorithms = {
            effUsername: {
                wordCapitalize: options.wordCapitalize,
                wordIncludeNumber: options.wordIncludeNumber,
                website: options.website,
            },
            subaddress: {
                subaddressType: options.subaddressType,
                subaddressEmail: options.subaddressEmail,
                website: options.website,
            },
            catchall: {
                catchallType: options.catchallType,
                catchallDomain: options.catchallDomain,
                website: options.website,
            },
        };
        return { generator, algorithms, forwarders };
    }
    toUsernameOptions(options) {
        return {
            type: options.generator.username,
            wordCapitalize: options.algorithms.effUsername.wordCapitalize,
            wordIncludeNumber: options.algorithms.effUsername.wordIncludeNumber,
            subaddressType: options.algorithms.subaddress.subaddressType,
            subaddressEmail: options.algorithms.subaddress.subaddressEmail,
            catchallType: options.algorithms.catchall.catchallType,
            catchallDomain: options.algorithms.catchall.catchallDomain,
            forwardedService: options.generator.forwarder,
            forwardedAnonAddyApiToken: options.forwarders.addyIo.token,
            forwardedAnonAddyDomain: options.forwarders.addyIo.domain,
            forwardedAnonAddyBaseUrl: options.forwarders.addyIo.baseUrl,
            forwardedDuckDuckGoToken: options.forwarders.duckDuckGo.token,
            forwardedFirefoxApiToken: options.forwarders.firefoxRelay.token,
            forwardedFastmailApiToken: options.forwarders.fastmail.token,
            forwardedForwardEmailApiToken: options.forwarders.forwardEmail.token,
            forwardedForwardEmailDomain: options.forwarders.forwardEmail.domain,
            forwardedSimpleLoginApiKey: options.forwarders.simpleLogin.token,
            forwardedSimpleLoginBaseUrl: options.forwarders.simpleLogin.baseUrl,
        };
    }
}

;// ../../libs/tools/generator/extensions/legacy/src/create-legacy-username-generation-service.ts




const { /* KeyServiceRandomizer */ "q4": bw_create_legacy_username_generation_service_KeyServiceRandomizer, /* UsernameRandomizer */ "QS": bw_create_legacy_username_generation_service_UsernameRandomizer, /* EmailRandomizer */ "Mt": bw_create_legacy_username_generation_service_EmailRandomizer, /* EmailCalculator */ "Lq": bw_create_legacy_username_generation_service_EmailCalculator } = bw_engine_namespaceObject;
const bw_create_legacy_username_generation_service_DefaultGeneratorService = bw_DefaultGeneratorService;
const { /* CatchallGeneratorStrategy */ "B": bw_create_legacy_username_generation_service_CatchallGeneratorStrategy, /* SubaddressGeneratorStrategy */ "Vm": bw_create_legacy_username_generation_service_SubaddressGeneratorStrategy, /* EffUsernameGeneratorStrategy */ "KQ": bw_create_legacy_username_generation_service_EffUsernameGeneratorStrategy, /* ForwarderGeneratorStrategy */ "ji": bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy, } = bw_strategies_namespaceObject;
function bw_legacyUsernameGenerationServiceFactory(apiService, i18nService, keyService, encryptService, policyService, accountService, stateProvider) {
    const randomizer = new bw_create_legacy_username_generation_service_KeyServiceRandomizer(keyService);
    const restClient = new RestClient(apiService, i18nService);
    const usernameRandomizer = new bw_create_legacy_username_generation_service_UsernameRandomizer(randomizer);
    const emailRandomizer = new bw_create_legacy_username_generation_service_EmailRandomizer(randomizer);
    const emailCalculator = new bw_create_legacy_username_generation_service_EmailCalculator();
    const effUsername = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_EffUsernameGeneratorStrategy(usernameRandomizer, stateProvider), policyService);
    const subaddress = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_SubaddressGeneratorStrategy(emailCalculator, emailRandomizer, stateProvider), policyService);
    const catchall = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_CatchallGeneratorStrategy(emailCalculator, emailRandomizer, stateProvider), policyService);
    const addyIo = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy(Integrations.AddyIo, restClient, i18nService, encryptService, keyService, stateProvider), policyService);
    const duckDuckGo = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy(Integrations.DuckDuckGo, restClient, i18nService, encryptService, keyService, stateProvider), policyService);
    const fastmail = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy(Integrations.Fastmail, restClient, i18nService, encryptService, keyService, stateProvider), policyService);
    const firefoxRelay = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy(Integrations.FirefoxRelay, restClient, i18nService, encryptService, keyService, stateProvider), policyService);
    const forwardEmail = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy(Integrations.ForwardEmail, restClient, i18nService, encryptService, keyService, stateProvider), policyService);
    const simpleLogin = new bw_create_legacy_username_generation_service_DefaultGeneratorService(new bw_create_legacy_username_generation_service_ForwarderGeneratorStrategy(Integrations.SimpleLogin, restClient, i18nService, encryptService, keyService, stateProvider), policyService);
    const navigation = new DefaultGeneratorNavigationService(stateProvider, policyService);
    return new LegacyUsernameGenerationService(accountService, navigation, catchall, effUsername, subaddress, addyIo, duckDuckGo, fastmail, firefoxRelay, forwardEmail, simpleLogin);
}

;// ../../libs/tools/generator/extensions/legacy/src/index.ts







;// ../../libs/importer/src/services/import-api.service.ts
var bw_import_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_ImportApiService {
    constructor(apiService) {
        this.apiService = apiService;
    }
    postImportCiphers(request) {
        return bw_import_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.apiService.send("POST", "/ciphers/import", request, true, false);
        });
    }
    postImportOrganizationCiphers(organizationId, request) {
        return bw_import_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.apiService.send("POST", "/ciphers/import-organization?organizationId=" + organizationId, request, true, false);
        });
    }
}

;// ../../libs/common/src/models/request/import-ciphers.request.ts
class bw_ImportCiphersRequest {
    constructor() {
        this.ciphers = [];
        this.folders = [];
        this.folderRelationships = [];
    }
}

;// ../../libs/common/src/models/request/import-organization-ciphers.request.ts
class bw_ImportOrganizationCiphersRequest {
    constructor() {
        this.ciphers = [];
        this.collections = [];
        this.collectionRelationships = [];
    }
}

;// ../../libs/common/src/models/request/kvp.request.ts
class bw_KvpRequest {
    constructor(key, value) {
        this.key = key;
        this.value = value;
    }
}

;// ../../libs/importer/src/models/import-result.ts
class bw_import_result_ImportResult {
    constructor() {
        this.success = false;
        this.ciphers = [];
        this.folders = [];
        this.folderRelationships = [];
        this.collections = [];
        this.collectionRelationships = [];
    }
}

;// ../../libs/common/src/platform/services/console-log.service.ts

class bw_console_log_service_ConsoleLogService {
    constructor(isDev, filter = null) {
        this.isDev = isDev;
        this.filter = filter;
        this.timersMap = new Map();
    }
    debug(message, ...optionalParams) {
        if (!this.isDev) {
            return;
        }
        this.write(bw_LogLevelType.Debug, message, ...optionalParams);
    }
    info(message, ...optionalParams) {
        this.write(bw_LogLevelType.Info, message, ...optionalParams);
    }
    warning(message, ...optionalParams) {
        this.write(bw_LogLevelType.Warning, message, ...optionalParams);
    }
    error(message, ...optionalParams) {
        this.write(bw_LogLevelType.Error, message, ...optionalParams);
    }
    write(level, message, ...optionalParams) {
        if (this.filter != null && this.filter(level)) {
            return;
        }
        switch (level) {
            case bw_LogLevelType.Debug:
                // eslint-disable-next-line
                console.log(message, ...optionalParams);
                break;
            case bw_LogLevelType.Info:
                // eslint-disable-next-line
                console.log(message, ...optionalParams);
                break;
            case bw_LogLevelType.Warning:
                // eslint-disable-next-line
                console.warn(message, ...optionalParams);
                break;
            case bw_LogLevelType.Error:
                // eslint-disable-next-line
                console.error(message, ...optionalParams);
                break;
            default:
                break;
        }
    }
}

;// ../../libs/importer/src/importers/base-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore












class bw_base_importer_BaseImporter {
    constructor() {
        this.organizationId = null;
        // FIXME: This should be replaced by injecting the log service.
        this.logService = new bw_console_log_service_ConsoleLogService(false);
        this.newLineRegex = /(?:\r\n|\r|\n)/;
        this.passwordFieldNames = [
            "password",
            "pass word",
            "passphrase",
            "pass phrase",
            "pass",
            "code",
            "code word",
            "codeword",
            "secret",
            "secret word",
            "personpwd",
            "key",
            "keyword",
            "key word",
            "keyphrase",
            "key phrase",
            "form_pw",
            "wppassword",
            "pin",
            "pwd",
            "pw",
            "pword",
            "passwd",
            "p",
            "serial",
            "serial#",
            "license key",
            "reg #",
            // Non-English names
            "passwort",
        ];
        this.usernameFieldNames = [
            "user",
            "name",
            "user name",
            "username",
            "login name",
            "email",
            "e-mail",
            "id",
            "userid",
            "user id",
            "login",
            "form_loginname",
            "wpname",
            "mail",
            "loginid",
            "login id",
            "log",
            "personlogin",
            "first name",
            "last name",
            "card#",
            "account #",
            "member",
            "member #",
            // Non-English names
            "nom",
            "benutzername",
        ];
        this.notesFieldNames = [
            "note",
            "notes",
            "comment",
            "comments",
            "memo",
            "description",
            "free form",
            "freeform",
            "free text",
            "freetext",
            "free",
            // Non-English names
            "kommentar",
        ];
        this.uriFieldNames = [
            "url",
            "hyper link",
            "hyperlink",
            "link",
            "host",
            "hostname",
            "host name",
            "server",
            "address",
            "hyper ref",
            "href",
            "web",
            "website",
            "web site",
            "site",
            "web-site",
            "uri",
            // Non-English names
            "ort",
            "adresse",
        ];
        this.parseCsvOptions = {
            encoding: "UTF-8",
            skipEmptyLines: false,
        };
    }
    get organization() {
        return this.organizationId != null;
    }
    parseXml(data) {
        // Ensure there are no external entity elements in the XML to prevent against XXE attacks.
        if (!this.validateNoExternalEntities(data)) {
            return null;
        }
        const parser = new DOMParser();
        const doc = parser.parseFromString(data, "application/xml");
        return doc != null && doc.querySelector("parsererror") == null ? doc : null;
    }
    parseCsv(data, header, options = {}) {
        const parseOptions = Object.assign({ header: header }, this.parseCsvOptions, options);
        data = this.splitNewLine(data).join("\n").trim();
        const result = bw_external_papaparse_namespaceObject.parse(data, parseOptions);
        if (result.errors != null && result.errors.length > 0) {
            result.errors.forEach((e) => {
                if (e.row != null) {
                    this.logService.warning("Error parsing row " + e.row + ": " + e.message);
                }
            });
        }
        return result.data && result.data.length > 0 ? result.data : null;
    }
    parseSingleRowCsv(rowData) {
        if (this.isNullOrWhitespace(rowData)) {
            return null;
        }
        const parsedRow = this.parseCsv(rowData, false);
        if (parsedRow != null && parsedRow.length > 0 && parsedRow[0].length > 0) {
            return parsedRow[0];
        }
        return null;
    }
    makeUriArray(uri) {
        if (uri == null) {
            return null;
        }
        if (typeof uri === "string") {
            const loginUri = new bw_LoginUriView();
            loginUri.uri = this.fixUri(uri);
            if (this.isNullOrWhitespace(loginUri.uri)) {
                return null;
            }
            loginUri.match = null;
            return [loginUri];
        }
        if (uri.length > 0) {
            const returnArr = [];
            uri.forEach((u) => {
                const loginUri = new bw_LoginUriView();
                loginUri.uri = this.fixUri(u);
                if (this.isNullOrWhitespace(loginUri.uri)) {
                    return;
                }
                loginUri.match = null;
                returnArr.push(loginUri);
            });
            return returnArr.length === 0 ? null : returnArr;
        }
        return null;
    }
    fixUri(uri) {
        if (uri == null) {
            return null;
        }
        uri = uri.trim();
        if (uri.indexOf("://") === -1 && uri.indexOf(".") >= 0) {
            uri = "http://" + uri;
        }
        if (uri.length > 1000) {
            return uri.substring(0, 1000);
        }
        return uri;
    }
    nameFromUrl(url) {
        const hostname = bw_utils_Utils.getHostname(url);
        if (this.isNullOrWhitespace(hostname)) {
            return null;
        }
        return hostname.startsWith("www.") ? hostname.replace("www.", "") : hostname;
    }
    isNullOrWhitespace(str) {
        return bw_utils_Utils.isNullOrWhitespace(str);
    }
    getValueOrDefault(str, defaultValue = null) {
        if (this.isNullOrWhitespace(str)) {
            return defaultValue;
        }
        return str;
    }
    splitNewLine(str) {
        return str.split(this.newLineRegex);
    }
    setCardExpiration(cipher, expiration) {
        if (this.isNullOrWhitespace(expiration)) {
            return false;
        }
        expiration = expiration.replace(/\s/g, "");
        const monthRegex = "0?(?<month>[1-9]|1[0-2])";
        const yearRegex = "(?<year>(?:[1-2][0-9])?[0-9]{2})";
        const expiryRegex = new RegExp(`^${monthRegex}/${yearRegex}$`);
        const expiryMatch = expiration.match(expiryRegex);
        if (!expiryMatch) {
            return false;
        }
        cipher.card.expMonth = expiryMatch.groups.month;
        const year = expiryMatch.groups.year;
        cipher.card.expYear = bw_normalizeExpiryYearFormat(year);
        return true;
    }
    moveFoldersToCollections(result) {
        result.folderRelationships.forEach((r) => result.collectionRelationships.push(r));
        result.collections = result.folders.map((f) => {
            const collection = new bw_CollectionView();
            collection.name = f.name;
            collection.id = f.id;
            return collection;
        });
        result.folderRelationships = [];
        result.folders = [];
    }
    querySelectorDirectChild(parentEl, query) {
        const els = this.querySelectorAllDirectChild(parentEl, query);
        return els.length === 0 ? null : els[0];
    }
    querySelectorAllDirectChild(parentEl, query) {
        return Array.from(parentEl.querySelectorAll(query)).filter((el) => el.parentNode === parentEl);
    }
    initLoginCipher() {
        const cipher = new bw_CipherView();
        cipher.favorite = false;
        cipher.notes = "";
        cipher.fields = [];
        cipher.login = new bw_LoginView();
        cipher.type = bw_CipherType.Login;
        return cipher;
    }
    cleanupCipher(cipher) {
        if (cipher == null) {
            return;
        }
        if (cipher.type !== bw_CipherType.Login) {
            cipher.login = null;
        }
        if (this.isNullOrWhitespace(cipher.name)) {
            cipher.name = "--";
        }
        if (this.isNullOrWhitespace(cipher.notes)) {
            cipher.notes = null;
        }
        else {
            cipher.notes = cipher.notes.trim();
        }
        if (cipher.fields != null && cipher.fields.length === 0) {
            cipher.fields = null;
        }
        if (cipher.passwordHistory != null && cipher.passwordHistory.length === 0) {
            cipher.passwordHistory = null;
        }
    }
    processKvp(cipher, key, value, type = bw_FieldType.Text) {
        if (this.isNullOrWhitespace(value)) {
            return;
        }
        if (this.isNullOrWhitespace(key)) {
            key = "";
        }
        if (value.length > 200 || value.trim().search(this.newLineRegex) > -1) {
            if (cipher.notes == null) {
                cipher.notes = "";
            }
            cipher.notes += key + ": " + this.splitNewLine(value).join("\n") + "\n";
        }
        else {
            if (cipher.fields == null) {
                cipher.fields = [];
            }
            const field = new bw_FieldView();
            field.type = type;
            field.name = key;
            field.value = value;
            cipher.fields.push(field);
        }
    }
    processFolder(result, folderName, addRelationship = true) {
        if (this.isNullOrWhitespace(folderName)) {
            return;
        }
        let folderIndex = result.folders.length;
        // Replace backslashes with forward slashes, ensuring we create sub-folders
        folderName = folderName.replace("\\", "/");
        let addFolder = true;
        for (let i = 0; i < result.folders.length; i++) {
            if (result.folders[i].name === folderName) {
                addFolder = false;
                folderIndex = i;
                break;
            }
        }
        if (addFolder) {
            const f = new bw_FolderView();
            f.name = folderName;
            result.folders.push(f);
        }
        //Some folders can have sub-folders but no ciphers directly, we should not add to the folderRelationships array
        if (addRelationship) {
            result.folderRelationships.push([result.ciphers.length, folderIndex]);
        }
    }
    convertToNoteIfNeeded(cipher) {
        if (cipher.type === bw_CipherType.Login &&
            this.isNullOrWhitespace(cipher.login.username) &&
            this.isNullOrWhitespace(cipher.login.password) &&
            (cipher.login.uris == null || cipher.login.uris.length === 0)) {
            cipher.type = bw_CipherType.SecureNote;
            cipher.secureNote = new bw_SecureNoteView();
            cipher.secureNote.type = bw_SecureNoteType.Generic;
        }
    }
    processFullName(cipher, fullName) {
        if (this.isNullOrWhitespace(fullName)) {
            return;
        }
        const nameParts = fullName.split(" ");
        if (nameParts.length > 0) {
            cipher.identity.firstName = this.getValueOrDefault(nameParts[0]);
        }
        if (nameParts.length === 2) {
            cipher.identity.lastName = this.getValueOrDefault(nameParts[1]);
        }
        else if (nameParts.length >= 3) {
            cipher.identity.middleName = this.getValueOrDefault(nameParts[1]);
            cipher.identity.lastName = nameParts.slice(2, nameParts.length).join(" ");
        }
    }
    validateNoExternalEntities(data) {
        const regex = new RegExp("<!ENTITY", "i");
        const hasExternalEntities = regex.test(data);
        return !hasExternalEntities;
    }
}

;// ../../libs/importer/src/importers/ascendo-csv-importer.ts


class bw_AscendoCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length < 2) {
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValueOrDefault(value[value.length - 1]);
            cipher.name = this.getValueOrDefault(value[0], "--");
            if (value.length > 2 && value.length % 2 === 0) {
                for (let i = 0; i < value.length - 2; i += 2) {
                    const val = value[i + 2];
                    const field = value[i + 1];
                    if (this.isNullOrWhitespace(val) || this.isNullOrWhitespace(field)) {
                        continue;
                    }
                    const fieldLower = field.toLowerCase();
                    if (cipher.login.password == null && this.passwordFieldNames.indexOf(fieldLower) > -1) {
                        cipher.login.password = this.getValueOrDefault(val);
                    }
                    else if (cipher.login.username == null &&
                        this.usernameFieldNames.indexOf(fieldLower) > -1) {
                        cipher.login.username = this.getValueOrDefault(val);
                    }
                    else if ((cipher.login.uris == null || cipher.login.uris.length === 0) &&
                        this.uriFieldNames.indexOf(fieldLower) > -1) {
                        cipher.login.uris = this.makeUriArray(val);
                    }
                    else {
                        this.processKvp(cipher, field, val);
                    }
                }
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/avast/avast-csv-importer.ts


class bw_AvastCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.name);
            cipher.login.uris = this.makeUriArray(value.web);
            cipher.login.password = this.getValueOrDefault(value.password);
            cipher.login.username = this.getValueOrDefault(value.login);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/avast/avast-json-importer.ts




class bw_AvastJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        if (results.logins != null) {
            results.logins.forEach((value) => {
                const cipher = this.initLoginCipher();
                cipher.name = this.getValueOrDefault(value.custName);
                cipher.notes = this.getValueOrDefault(value.note);
                cipher.login.uris = this.makeUriArray(value.url);
                cipher.login.password = this.getValueOrDefault(value.pwd);
                cipher.login.username = this.getValueOrDefault(value.loginName);
                this.cleanupCipher(cipher);
                result.ciphers.push(cipher);
            });
        }
        if (results.notes != null) {
            results.notes.forEach((value) => {
                const cipher = this.initLoginCipher();
                cipher.type = bw_CipherType.SecureNote;
                cipher.secureNote.type = bw_SecureNoteType.Generic;
                cipher.name = this.getValueOrDefault(value.label);
                cipher.notes = this.getValueOrDefault(value.text);
                this.cleanupCipher(cipher);
                result.ciphers.push(cipher);
            });
        }
        if (results.cards != null) {
            results.cards.forEach((value) => {
                const cipher = this.initLoginCipher();
                cipher.type = bw_CipherType.Card;
                cipher.name = this.getValueOrDefault(value.custName);
                cipher.notes = this.getValueOrDefault(value.note);
                cipher.card.cardholderName = this.getValueOrDefault(value.holderName);
                cipher.card.number = this.getValueOrDefault(value.cardNumber);
                cipher.card.code = this.getValueOrDefault(value.cvv);
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                if (value.expirationDate != null) {
                    if (value.expirationDate.month != null) {
                        cipher.card.expMonth = value.expirationDate.month + "";
                    }
                    if (value.expirationDate.year != null) {
                        cipher.card.expYear = value.expirationDate.year + "";
                    }
                }
                this.cleanupCipher(cipher);
                result.ciphers.push(cipher);
            });
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/avast/index.ts



;// ../../libs/importer/src/importers/avira-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_AviraCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.name, this.getValueOrDefault(this.nameFromUrl(value.website), "--"));
            cipher.login.uris = this.makeUriArray(value.website);
            cipher.login.password = this.getValueOrDefault(value.password);
            if (this.isNullOrWhitespace(value.username) &&
                !this.isNullOrWhitespace(value.secondary_username)) {
                cipher.login.username = value.secondary_username;
            }
            else {
                cipher.login.username = this.getValueOrDefault(value.username);
                cipher.notes = this.getValueOrDefault(value.secondary_username);
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/blackberry-csv-importer.ts


class bw_BlackBerryCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.grouping === "list") {
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.favorite = value.fav === "1";
            cipher.name = this.getValueOrDefault(value.name);
            cipher.notes = this.getValueOrDefault(value.extra);
            if (value.grouping !== "note") {
                cipher.login.uris = this.makeUriArray(value.url);
                cipher.login.password = this.getValueOrDefault(value.password);
                cipher.login.username = this.getValueOrDefault(value.username);
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/chrome-csv-importer.ts


class bw_ChromeCsvImporter extends bw_base_importer_BaseImporter {
    constructor() {
        super(...arguments);
        this.androidPatternRegex = new RegExp("^android:\\/\\/.*(?<=@)(.*)(?=\\/)");
    }
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            let name = value.name;
            if (!name && this.androidPatternRegex.test(value.url)) {
                name = value.url.match(this.androidPatternRegex)[1];
            }
            cipher.name = this.getValueOrDefault(name, "--");
            cipher.login.username = this.getValueOrDefault(value.username);
            cipher.login.password = this.getValueOrDefault(value.password);
            cipher.login.uris = this.makeUriArray(value.url);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/bitwarden/bitwarden-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore









class bw_BitwardenCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (this.organization && !this.isNullOrWhitespace(value.collections)) {
                const collections = value.collections.split(",");
                collections.forEach((col) => {
                    let addCollection = true;
                    let collectionIndex = result.collections.length;
                    for (let i = 0; i < result.collections.length; i++) {
                        if (result.collections[i].name === col) {
                            addCollection = false;
                            collectionIndex = i;
                            break;
                        }
                    }
                    if (addCollection) {
                        const collection = new bw_CollectionView();
                        collection.name = col;
                        result.collections.push(collection);
                    }
                    result.collectionRelationships.push([result.ciphers.length, collectionIndex]);
                    // if the collection name is a/b/c/d, we need to create a/b/c and a/b and a
                    const parts = col.split("/");
                    for (let i = parts.length - 1; i > 0; i--) {
                        const parentCollectionName = parts.slice(0, i).join("/");
                        if (result.collections.find((c) => c.name === parentCollectionName) == null) {
                            const parentCollection = new bw_CollectionView();
                            parentCollection.name = parentCollectionName;
                            result.collections.push(parentCollection);
                        }
                    }
                });
            }
            else if (!this.organization) {
                this.processFolder(result, value.folder);
            }
            const cipher = new bw_CipherView();
            cipher.favorite =
                !this.organization && this.getValueOrDefault(value.favorite, "0") !== "0" ? true : false;
            cipher.type = bw_CipherType.Login;
            cipher.notes = this.getValueOrDefault(value.notes);
            cipher.name = this.getValueOrDefault(value.name, "--");
            try {
                cipher.reprompt = parseInt(this.getValueOrDefault(value.reprompt, bw_CipherRepromptType.None.toString()), 10);
            }
            catch (e) {
                // eslint-disable-next-line
                console.error("Unable to parse reprompt value", e);
                cipher.reprompt = bw_CipherRepromptType.None;
            }
            if (!this.isNullOrWhitespace(value.fields)) {
                const fields = this.splitNewLine(value.fields);
                for (let i = 0; i < fields.length; i++) {
                    if (this.isNullOrWhitespace(fields[i])) {
                        continue;
                    }
                    const delimPosition = fields[i].lastIndexOf(": ");
                    if (delimPosition === -1) {
                        continue;
                    }
                    if (cipher.fields == null) {
                        cipher.fields = [];
                    }
                    const field = new bw_FieldView();
                    field.name = fields[i].substr(0, delimPosition);
                    field.value = null;
                    field.type = bw_FieldType.Text;
                    if (fields[i].length > delimPosition + 2) {
                        field.value = fields[i].substr(delimPosition + 2);
                    }
                    cipher.fields.push(field);
                }
            }
            const valueType = value.type != null ? value.type.toLowerCase() : null;
            switch (valueType) {
                case "note":
                    cipher.type = bw_CipherType.SecureNote;
                    cipher.secureNote = new bw_SecureNoteView();
                    cipher.secureNote.type = bw_SecureNoteType.Generic;
                    break;
                default: {
                    cipher.type = bw_CipherType.Login;
                    cipher.login = new bw_LoginView();
                    cipher.login.totp = this.getValueOrDefault(value.login_totp || value.totp);
                    cipher.login.username = this.getValueOrDefault(value.login_username || value.username);
                    cipher.login.password = this.getValueOrDefault(value.login_password || value.password);
                    const uris = this.parseSingleRowCsv(value.login_uri || value.uri);
                    cipher.login.uris = this.makeUriArray(uris);
                    break;
                }
            }
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/bitwarden/bitwarden-json-importer.ts
var bw_bitwarden_json_importer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_BitwardenJsonImporter extends bw_base_importer_BaseImporter {
    constructor(keyService, encryptService, i18nService, cipherService, pinService, accountService) {
        super();
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.i18nService = i18nService;
        this.cipherService = cipherService;
        this.pinService = pinService;
        this.accountService = accountService;
    }
    parse(data) {
        return bw_bitwarden_json_importer_awaiter(this, void 0, void 0, function* () {
            this.result = new bw_import_result_ImportResult();
            const results = JSON.parse(data);
            if (results == null || results.items == null) {
                this.result.success = false;
                return this.result;
            }
            if (results.encrypted) {
                yield this.parseEncrypted(results);
            }
            else {
                yield this.parseDecrypted(results);
            }
            return this.result;
        });
    }
    parseEncrypted(results) {
        return bw_bitwarden_json_importer_awaiter(this, void 0, void 0, function* () {
            if (results.encKeyValidation_DO_NOT_EDIT != null) {
                let keyForDecryption = yield this.keyService.getOrgKey(this.organizationId);
                if (keyForDecryption == null) {
                    keyForDecryption = yield this.keyService.getUserKeyWithLegacySupport();
                }
                const encKeyValidation = new bw_enc_string_EncString(results.encKeyValidation_DO_NOT_EDIT);
                const encKeyValidationDecrypt = yield this.encryptService.decryptToUtf8(encKeyValidation, keyForDecryption);
                if (encKeyValidationDecrypt === null) {
                    this.result.success = false;
                    this.result.errorMessage = this.i18nService.t("importEncKeyError");
                    return;
                }
            }
            const groupingsMap = this.organization
                ? yield this.parseCollections(results)
                : yield this.parseFolders(results);
            for (const c of results.items) {
                const cipher = bw_CipherWithIdExport.toDomain(c);
                // reset ids incase they were set for some reason
                cipher.id = null;
                cipher.organizationId = this.organizationId;
                cipher.collectionIds = null;
                // make sure password history is limited
                if (cipher.passwordHistory != null && cipher.passwordHistory.length > 5) {
                    cipher.passwordHistory = cipher.passwordHistory.slice(0, 5);
                }
                if (!this.organization && c.folderId != null && groupingsMap.has(c.folderId)) {
                    this.result.folderRelationships.push([
                        this.result.ciphers.length,
                        groupingsMap.get(c.folderId),
                    ]);
                }
                else if (this.organization && c.collectionIds != null) {
                    c.collectionIds.forEach((cId) => {
                        if (groupingsMap.has(cId)) {
                            this.result.collectionRelationships.push([
                                this.result.ciphers.length,
                                groupingsMap.get(cId),
                            ]);
                        }
                    });
                }
                const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
                const view = yield cipher.decrypt(yield this.cipherService.getKeyForCipherKeyDecryption(cipher, activeUserId));
                this.cleanupCipher(view);
                this.result.ciphers.push(view);
            }
            this.result.success = true;
        });
    }
    parseDecrypted(results) {
        return bw_bitwarden_json_importer_awaiter(this, void 0, void 0, function* () {
            const groupingsMap = this.organization
                ? yield this.parseCollections(results)
                : yield this.parseFolders(results);
            results.items.forEach((c) => {
                const cipher = bw_CipherWithIdExport.toView(c);
                // reset ids incase they were set for some reason
                cipher.id = null;
                cipher.organizationId = null;
                cipher.collectionIds = null;
                // make sure password history is limited
                if (cipher.passwordHistory != null && cipher.passwordHistory.length > 5) {
                    cipher.passwordHistory = cipher.passwordHistory.slice(0, 5);
                }
                if (!this.organization && c.folderId != null && groupingsMap.has(c.folderId)) {
                    this.result.folderRelationships.push([
                        this.result.ciphers.length,
                        groupingsMap.get(c.folderId),
                    ]);
                }
                else if (this.organization && c.collectionIds != null) {
                    c.collectionIds.forEach((cId) => {
                        if (groupingsMap.has(cId)) {
                            this.result.collectionRelationships.push([
                                this.result.ciphers.length,
                                groupingsMap.get(cId),
                            ]);
                        }
                    });
                }
                this.cleanupCipher(cipher);
                this.result.ciphers.push(cipher);
            });
            this.result.success = true;
        });
    }
    parseFolders(data) {
        return bw_bitwarden_json_importer_awaiter(this, void 0, void 0, function* () {
            if (data.folders == null) {
                return null;
            }
            const groupingsMap = new Map();
            for (const f of data.folders) {
                let folderView;
                if (data.encrypted) {
                    const folder = bw_FolderWithIdExport.toDomain(f);
                    if (folder != null) {
                        folderView = yield folder.decrypt();
                    }
                }
                else {
                    folderView = bw_FolderWithIdExport.toView(f);
                }
                if (folderView != null) {
                    groupingsMap.set(f.id, this.result.folders.length);
                    this.result.folders.push(folderView);
                }
            }
            return groupingsMap;
        });
    }
    parseCollections(data) {
        return bw_bitwarden_json_importer_awaiter(this, void 0, void 0, function* () {
            if (data.collections == null) {
                return null;
            }
            const groupingsMap = new Map();
            for (const c of data.collections) {
                let collectionView;
                if (data.encrypted) {
                    const collection = bw_CollectionWithIdExport.toDomain(c);
                    collection.organizationId = this.organizationId;
                    collectionView = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.keyService.activeUserOrgKeys$).then((orgKeys) => collection.decrypt(orgKeys[c.organizationId]));
                }
                else {
                    collectionView = bw_CollectionWithIdExport.toView(c);
                    collectionView.organizationId = null;
                }
                if (collectionView != null) {
                    groupingsMap.set(c.id, this.result.collections.length);
                    this.result.collections.push(collectionView);
                }
            }
            return groupingsMap;
        });
    }
}

;// ../../libs/importer/src/importers/bitwarden/bitwarden-password-protected-importer.ts
var bw_bitwarden_password_protected_importer_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};




class bw_BitwardenPasswordProtectedImporter extends bw_BitwardenJsonImporter {
    constructor(keyService, encryptService, i18nService, cipherService, pinService, accountService, promptForPassword_callback) {
        super(keyService, encryptService, i18nService, cipherService, pinService, accountService);
        this.promptForPassword_callback = promptForPassword_callback;
    }
    parse(data) {
        const _super = Object.create(null, {
            parse: { get: () => super.parse }
        });
        return bw_bitwarden_password_protected_importer_awaiter(this, void 0, void 0, function* () {
            const result = new bw_import_result_ImportResult();
            const parsedData = JSON.parse(data);
            if (!parsedData) {
                result.success = false;
                return result;
            }
            // File is unencrypted
            if (!(parsedData === null || parsedData === void 0 ? void 0 : parsedData.encrypted)) {
                return yield _super.parse.call(this, data);
            }
            // File is account-encrypted
            if (!(parsedData === null || parsedData === void 0 ? void 0 : parsedData.passwordProtected)) {
                return yield _super.parse.call(this, data);
            }
            if (this.cannotParseFile(parsedData)) {
                result.success = false;
                return result;
            }
            // File is password-protected
            const password = yield this.promptForPassword_callback();
            if (!(yield this.checkPassword(parsedData, password))) {
                result.success = false;
                result.errorMessage = this.i18nService.t("invalidFilePassword");
                return result;
            }
            const encData = new bw_enc_string_EncString(parsedData.data);
            const clearTextData = yield this.encryptService.decryptToUtf8(encData, this.key);
            return yield _super.parse.call(this, clearTextData);
        });
    }
    checkPassword(jdoc, password) {
        return bw_bitwarden_password_protected_importer_awaiter(this, void 0, void 0, function* () {
            if (this.isNullOrWhitespace(password)) {
                return false;
            }
            const kdfConfig = jdoc.kdfType === bw_KdfType.PBKDF2_SHA256
                ? new bw_PBKDF2KdfConfig(jdoc.kdfIterations)
                : new bw_Argon2KdfConfig(jdoc.kdfIterations, jdoc.kdfMemory, jdoc.kdfParallelism);
            this.key = yield this.pinService.makePinKey(password, jdoc.salt, kdfConfig);
            const encKeyValidation = new bw_enc_string_EncString(jdoc.encKeyValidation_DO_NOT_EDIT);
            const encKeyValidationDecrypt = yield this.encryptService.decryptToUtf8(encKeyValidation, this.key);
            if (encKeyValidationDecrypt === null) {
                return false;
            }
            return true;
        });
    }
    cannotParseFile(jdoc) {
        return (!jdoc ||
            !jdoc.encrypted ||
            !jdoc.passwordProtected ||
            !jdoc.salt ||
            !jdoc.kdfIterations ||
            typeof jdoc.kdfIterations !== "number" ||
            jdoc.kdfType == null ||
            bw_KdfType[jdoc.kdfType] == null ||
            !jdoc.encKeyValidation_DO_NOT_EDIT ||
            !jdoc.data);
    }
}

;// ../../libs/importer/src/importers/bitwarden/index.ts




;// ../../libs/importer/src/importers/blur-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_BlurCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.label === "null") {
                value.label = null;
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.label, this.getValueOrDefault(this.nameFromUrl(value.domain), "--"));
            cipher.login.uris = this.makeUriArray(value.domain);
            cipher.login.password = this.getValueOrDefault(value.password);
            if (this.isNullOrWhitespace(value.email) && !this.isNullOrWhitespace(value.username)) {
                cipher.login.username = value.username;
            }
            else {
                cipher.login.username = this.getValueOrDefault(value.email);
                cipher.notes = this.getValueOrDefault(value.username);
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/buttercup-csv-importer.ts


const bw_OfficialProps = ["!group_id", "!group_name", "title", "username", "password", "URL", "id"];
class bw_ButtercupCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            this.processFolder(result, this.getValueOrDefault(value["!group_name"]));
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.title, "--");
            cipher.login.username = this.getValueOrDefault(value.username);
            cipher.login.password = this.getValueOrDefault(value.password);
            cipher.login.uris = this.makeUriArray(value.URL);
            let processingCustomFields = false;
            for (const prop in value) {
                // eslint-disable-next-line
                if (value.hasOwnProperty(prop)) {
                    if (!processingCustomFields && bw_OfficialProps.indexOf(prop) === -1) {
                        processingCustomFields = true;
                    }
                    if (processingCustomFields) {
                        this.processKvp(cipher, prop, value[prop]);
                    }
                }
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/clipperz-html-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_ClipperzHtmlImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const doc = this.parseXml(data);
        if (doc == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        const textarea = doc.querySelector("textarea");
        if (textarea == null || this.isNullOrWhitespace(textarea.textContent)) {
            result.errorMessage = "Missing textarea.";
            result.success = false;
            return Promise.resolve(result);
        }
        const entries = JSON.parse(textarea.textContent);
        entries.forEach((entry) => {
            const cipher = this.initLoginCipher();
            if (!this.isNullOrWhitespace(entry.label)) {
                cipher.name = entry.label.split(" ")[0];
            }
            if (entry.data != null && !this.isNullOrWhitespace(entry.data.notes)) {
                cipher.notes = entry.data.notes.split("\\n").join("\n");
            }
            if (entry.currentVersion != null && entry.currentVersion.fields != null) {
                for (const property in entry.currentVersion.fields) {
                    // eslint-disable-next-line
                    if (!entry.currentVersion.fields.hasOwnProperty(property)) {
                        continue;
                    }
                    const field = entry.currentVersion.fields[property];
                    const actionType = field.actionType != null ? field.actionType.toLowerCase() : null;
                    switch (actionType) {
                        case "password":
                            cipher.login.password = this.getValueOrDefault(field.value);
                            break;
                        case "email":
                        case "username":
                        case "user":
                        case "name":
                            cipher.login.username = this.getValueOrDefault(field.value);
                            break;
                        case "url":
                            cipher.login.uris = this.makeUriArray(field.value);
                            break;
                        default: {
                            const labelLower = field.label != null ? field.label.toLowerCase() : null;
                            if (cipher.login.password == null &&
                                this.passwordFieldNames.indexOf(labelLower) > -1) {
                                cipher.login.password = this.getValueOrDefault(field.value);
                            }
                            else if (cipher.login.username == null &&
                                this.usernameFieldNames.indexOf(labelLower) > -1) {
                                cipher.login.username = this.getValueOrDefault(field.value);
                            }
                            else if ((cipher.login.uris == null || cipher.login.uris.length === 0) &&
                                this.uriFieldNames.indexOf(labelLower) > -1) {
                                cipher.login.uris = this.makeUriArray(field.value);
                            }
                            else {
                                this.processKvp(cipher, field.label, field.value);
                            }
                            break;
                        }
                    }
                }
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/codebook-csv-importer.ts


class bw_CodebookCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            this.processFolder(result, this.getValueOrDefault(value.Category));
            const cipher = this.initLoginCipher();
            cipher.favorite = this.getValueOrDefault(value.Favorite) === "True";
            cipher.name = this.getValueOrDefault(value.Entry, "--");
            cipher.notes = this.getValueOrDefault(value.Note);
            cipher.login.username = this.getValueOrDefault(value.Username, value.Email);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.totp = this.getValueOrDefault(value.TOTP);
            cipher.login.uris = this.makeUriArray(value.Website);
            if (!this.isNullOrWhitespace(value.Username)) {
                this.processKvp(cipher, "Email", value.Email);
            }
            this.processKvp(cipher, "Phone", value.Phone);
            this.processKvp(cipher, "PIN", value.PIN);
            this.processKvp(cipher, "Account", value.Account);
            this.processKvp(cipher, "Date", value.Date);
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/dashlane/dashlane-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






const bw_mappedCredentialsColumns = new Set([
    "title",
    "note",
    "username",
    "password",
    "url",
    "otpSecret",
    "category",
]);
const bw_mappedPersonalInfoAsIdentityColumns = new Set([
    "type",
    "title",
    "first_name",
    "middle_name",
    "last_name",
    "login",
    "email",
    "phone_number",
    "address",
    "country",
    "state",
    "city",
    "zip",
    // Skip item_name as we already have set a combined name
    "item_name",
]);
const bw_mappedSecureNoteColumns = new Set(["title", "note"]);
class bw_DashlaneCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        if (results[0].type != null && results[0].title != null) {
            const personalRecords = results;
            // If personalRecords has only one "name" then create an Identity-Cipher
            if (personalRecords.filter((x) => x.type === "name").length === 1) {
                const cipher = this.initLoginCipher();
                cipher.type = bw_CipherType.Identity;
                cipher.identity = new bw_IdentityView();
                results.forEach((row) => {
                    this.parsePersonalInformationRecordAsIdentity(cipher, row);
                });
                this.cleanupCipher(cipher);
                result.ciphers.push(cipher);
                result.success = true;
                return Promise.resolve(result);
            }
        }
        results.forEach((row) => {
            const cipher = this.initLoginCipher();
            const rowKeys = Object.keys(row);
            if (rowKeys[0] === "username") {
                this.processFolder(result, row.category);
                this.parseCredentialsRecord(cipher, row);
            }
            if (rowKeys[0] === "type" && rowKeys[1] === "account_name") {
                this.parsePaymentRecord(cipher, row);
            }
            if (rowKeys[0] === "type" && rowKeys[1] === "number") {
                this.parseIdRecord(cipher, row);
            }
            if ((rowKeys[0] === "type") != null && rowKeys[1] === "title") {
                this.parsePersonalInformationRecord(cipher, row);
            }
            if (rowKeys[0] === "title" && rowKeys[1] === "note") {
                this.parseSecureNoteRecords(cipher, row);
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    parseCredentialsRecord(cipher, row) {
        cipher.type = bw_CipherType.Login;
        cipher.login = new bw_LoginView();
        cipher.name = row.title;
        cipher.notes = row.note;
        cipher.login.username = row.username;
        cipher.login.password = row.password;
        cipher.login.totp = Object.keys(row).includes("otpUrl") ? row.otpUrl : row.otpSecret;
        cipher.login.uris = this.makeUriArray(row.url);
        this.importUnmappedFields(cipher, row, bw_mappedCredentialsColumns);
    }
    parsePaymentRecord(cipher, row) {
        cipher.type = bw_CipherType.Card;
        cipher.card = new bw_CardView();
        cipher.name = row.account_name;
        let mappedValues = [];
        switch (row.type) {
            case "credit_card":
                cipher.card.cardholderName = row.account_name;
                cipher.card.number = row.cc_number;
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                cipher.card.code = row.code;
                this.setCardExpiration(cipher, `${row.expiration_month}/${row.expiration_year}`);
                // If you add more mapped fields please extend this
                mappedValues = [
                    "account_name",
                    "account_holder",
                    "cc_number",
                    "code",
                    "expiration_month",
                    "expiration_year",
                ];
                break;
            case "bank":
                cipher.card.cardholderName = row.account_holder;
                cipher.card.number = row.account_number;
                // If you add more mapped fields please extend this
                mappedValues = ["account_name", "account_holder", "account_number"];
                break;
            default:
                break;
        }
        this.importUnmappedFields(cipher, row, new Set(mappedValues));
    }
    parseIdRecord(cipher, row) {
        cipher.type = bw_CipherType.Identity;
        cipher.identity = new bw_IdentityView();
        const mappedValues = ["name", "number"];
        switch (row.type) {
            case "card":
                cipher.name = `${row.name} ${row.type}`;
                this.processFullName(cipher, row.name);
                cipher.identity.licenseNumber = row.number;
                break;
            case "passport":
                cipher.name = `${row.name} ${row.type}`;
                this.processFullName(cipher, row.name);
                cipher.identity.passportNumber = row.number;
                break;
            case "license":
                cipher.name = `${row.name} ${row.type}`;
                this.processFullName(cipher, row.name);
                cipher.identity.licenseNumber = row.number;
                cipher.identity.state = row.state;
                mappedValues.push("state");
                break;
            case "social_security":
                cipher.name = `${row.name} ${row.type}`;
                this.processFullName(cipher, row.name);
                cipher.identity.ssn = row.number;
                break;
            case "tax_number":
                cipher.name = row.type;
                cipher.identity.licenseNumber = row.number;
                break;
            default:
                break;
        }
        // If you add more mapped fields please extend this
        this.importUnmappedFields(cipher, row, new Set(mappedValues));
    }
    parsePersonalInformationRecord(cipher, row) {
        cipher.type = bw_CipherType.SecureNote;
        cipher.secureNote.type = bw_SecureNoteType.Generic;
        if (row.type === "name") {
            cipher.name = `${row.title} ${row.first_name} ${row.middle_name} ${row.last_name}`
                .replace("  ", " ")
                .trim();
        }
        else {
            cipher.name = row.item_name;
        }
        const dataRow = row;
        Object.keys(row).forEach((key) => {
            this.processKvp(cipher, key, dataRow[key]);
        });
    }
    parsePersonalInformationRecordAsIdentity(cipher, row) {
        switch (row.type) {
            case "name":
                this.processFullName(cipher, `${row.first_name} ${row.middle_name} ${row.last_name}`);
                cipher.identity.title = row.title;
                cipher.name = cipher.identity.fullName;
                cipher.identity.username = row.login;
                break;
            case "email":
                cipher.identity.email = row.email;
                break;
            case "number":
                cipher.identity.phone = row.phone_number;
                break;
            case "address":
                cipher.identity.address1 = row.address;
                cipher.identity.city = row.city;
                cipher.identity.postalCode = row.zip;
                cipher.identity.state = row.state;
                cipher.identity.country = row.country;
                break;
            default:
                break;
        }
        this.importUnmappedFields(cipher, row, bw_mappedPersonalInfoAsIdentityColumns);
    }
    parseSecureNoteRecords(cipher, row) {
        cipher.type = bw_CipherType.SecureNote;
        cipher.secureNote.type = bw_SecureNoteType.Generic;
        cipher.name = row.title;
        cipher.notes = row.note;
        this.importUnmappedFields(cipher, row, bw_mappedSecureNoteColumns);
    }
    importUnmappedFields(cipher, row, mappedValues) {
        const unmappedFields = Object.keys(row).filter((x) => !mappedValues.has(x));
        unmappedFields.forEach((key) => {
            const item = row;
            this.processKvp(cipher, key, item[key]);
        });
    }
}

;// ../../libs/importer/src/importers/dashlane/dashlane-json-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore







const bw_HandledResults = new Set([
    "ADDRESS",
    "AUTHENTIFIANT",
    "BANKSTATEMENT",
    "IDCARD",
    "IDENTITY",
    "PAYMENTMEANS_CREDITCARD",
    "PAYMENTMEAN_PAYPAL",
    "EMAIL",
]);
class bw_DashlaneJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        this.result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || results.length === 0) {
            this.result.success = false;
            return Promise.resolve(this.result);
        }
        if (results.ADDRESS != null) {
            this.processAddress(results.ADDRESS);
        }
        if (results.AUTHENTIFIANT != null) {
            this.processAuth(results.AUTHENTIFIANT);
        }
        if (results.BANKSTATEMENT != null) {
            this.processNote(results.BANKSTATEMENT, "BankAccountName");
        }
        if (results.IDCARD != null) {
            this.processNote(results.IDCARD, "Fullname");
        }
        if (results.PAYMENTMEANS_CREDITCARD != null) {
            this.processCard(results.PAYMENTMEANS_CREDITCARD);
        }
        if (results.IDENTITY != null) {
            this.processIdentity(results.IDENTITY);
        }
        for (const key in results) {
            // eslint-disable-next-line
            if (results.hasOwnProperty(key) && !bw_HandledResults.has(key)) {
                this.processNote(results[key], null, "Generic Note");
            }
        }
        this.result.success = true;
        return Promise.resolve(this.result);
    }
    processAuth(results) {
        results.forEach((credential) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(credential.title);
            cipher.login.username = this.getValueOrDefault(credential.login, this.getValueOrDefault(credential.secondaryLogin));
            if (this.isNullOrWhitespace(cipher.login.username)) {
                cipher.login.username = this.getValueOrDefault(credential.email);
            }
            else if (!this.isNullOrWhitespace(credential.email)) {
                cipher.notes = "Email: " + credential.email + "\n";
            }
            cipher.login.password = this.getValueOrDefault(credential.password);
            cipher.login.uris = this.makeUriArray(credential.domain);
            cipher.notes += this.getValueOrDefault(credential.note, "");
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
        });
    }
    processIdentity(results) {
        results.forEach((obj) => {
            const cipher = new bw_CipherView();
            cipher.identity = new bw_IdentityView();
            cipher.type = bw_CipherType.Identity;
            cipher.name = this.getValueOrDefault(obj.fullName, "");
            const nameParts = cipher.name.split(" ");
            if (nameParts.length > 0) {
                cipher.identity.firstName = this.getValueOrDefault(nameParts[0]);
            }
            if (nameParts.length === 2) {
                cipher.identity.lastName = this.getValueOrDefault(nameParts[1]);
            }
            else if (nameParts.length === 3) {
                cipher.identity.middleName = this.getValueOrDefault(nameParts[1]);
                cipher.identity.lastName = this.getValueOrDefault(nameParts[2]);
            }
            cipher.identity.username = this.getValueOrDefault(obj.pseudo);
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
        });
    }
    processAddress(results) {
        results.forEach((obj) => {
            const cipher = new bw_CipherView();
            cipher.identity = new bw_IdentityView();
            cipher.type = bw_CipherType.Identity;
            cipher.name = this.getValueOrDefault(obj.addressName);
            cipher.identity.address1 = this.getValueOrDefault(obj.addressFull);
            cipher.identity.city = this.getValueOrDefault(obj.city);
            cipher.identity.state = this.getValueOrDefault(obj.state);
            cipher.identity.postalCode = this.getValueOrDefault(obj.zipcode);
            cipher.identity.country = this.getValueOrDefault(obj.country);
            if (cipher.identity.country != null) {
                cipher.identity.country = cipher.identity.country.toUpperCase();
            }
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
        });
    }
    processCard(results) {
        results.forEach((obj) => {
            const cipher = new bw_CipherView();
            cipher.card = new bw_CardView();
            cipher.type = bw_CipherType.Card;
            cipher.name = this.getValueOrDefault(obj.bank);
            cipher.card.number = this.getValueOrDefault(obj.cardNumber);
            cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
            cipher.card.cardholderName = this.getValueOrDefault(obj.owner);
            if (!this.isNullOrWhitespace(cipher.card.brand)) {
                if (this.isNullOrWhitespace(cipher.name)) {
                    cipher.name = cipher.card.brand;
                }
                else {
                    cipher.name += " - " + cipher.card.brand;
                }
            }
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
        });
    }
    processNote(results, nameProperty, name = null) {
        results.forEach((obj) => {
            const cipher = new bw_CipherView();
            cipher.secureNote = new bw_SecureNoteView();
            cipher.type = bw_CipherType.SecureNote;
            cipher.secureNote.type = bw_SecureNoteType.Generic;
            if (name != null) {
                cipher.name = name;
            }
            else {
                cipher.name = this.getValueOrDefault(obj[nameProperty]);
            }
            for (const key in obj) {
                // eslint-disable-next-line
                if (obj.hasOwnProperty(key) && key !== nameProperty) {
                    this.processKvp(cipher, key, obj[key].toString());
                }
            }
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
        });
    }
}

;// ../../libs/importer/src/importers/dashlane/index.ts



;// ../../libs/importer/src/importers/encryptr-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_EncryptrCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.Label, "--");
            cipher.notes = this.getValueOrDefault(value.Notes);
            const text = this.getValueOrDefault(value.Text);
            if (!this.isNullOrWhitespace(text)) {
                if (this.isNullOrWhitespace(cipher.notes)) {
                    cipher.notes = text;
                }
                else {
                    cipher.notes += "\n\n" + text;
                }
            }
            const type = value["Entry Type"];
            if (type === "Password") {
                cipher.login.username = this.getValueOrDefault(value.Username);
                cipher.login.password = this.getValueOrDefault(value.Password);
                cipher.login.uris = this.makeUriArray(value["Site URL"]);
            }
            else if (type === "Credit Card") {
                cipher.type = bw_CipherType.Card;
                cipher.card = new bw_CardView();
                cipher.card.cardholderName = this.getValueOrDefault(value["Name on card"]);
                cipher.card.number = this.getValueOrDefault(value["Card Number"]);
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                cipher.card.code = this.getValueOrDefault(value.CVV);
                const expiry = this.getValueOrDefault(value.Expiry);
                if (!this.isNullOrWhitespace(expiry)) {
                    const expParts = expiry.split("/");
                    if (expParts.length > 1) {
                        cipher.card.expMonth = parseInt(expParts[0], null).toString();
                        cipher.card.expYear = (2000 + parseInt(expParts[1], null)).toString();
                    }
                }
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/enpass/enpass-csv-importer.ts





class bw_EnpassCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        let firstRow = true;
        results.forEach((value) => {
            if (value.length < 2 || (firstRow && (value[0] === "Title" || value[0] === "title"))) {
                firstRow = false;
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValueOrDefault(value[value.length - 1]);
            cipher.name = this.getValueOrDefault(value[0], "--");
            if (value.length === 2 ||
                (!this.containsField(value, "username") &&
                    !this.containsField(value, "password") &&
                    !this.containsField(value, "email") &&
                    !this.containsField(value, "url"))) {
                cipher.type = bw_CipherType.SecureNote;
                cipher.secureNote = new bw_SecureNoteView();
                cipher.secureNote.type = bw_SecureNoteType.Generic;
            }
            if (this.containsField(value, "cardholder") &&
                this.containsField(value, "number") &&
                this.containsField(value, "expiry date")) {
                cipher.type = bw_CipherType.Card;
                cipher.card = new bw_CardView();
            }
            if (value.length > 2 && value.length % 2 === 0) {
                for (let i = 0; i < value.length - 2; i += 2) {
                    const fieldValue = value[i + 2];
                    if (this.isNullOrWhitespace(fieldValue)) {
                        continue;
                    }
                    const fieldName = value[i + 1];
                    const fieldNameLower = fieldName.toLowerCase();
                    if (cipher.type === bw_CipherType.Login) {
                        if (fieldNameLower === "url" &&
                            (cipher.login.uris == null || cipher.login.uris.length === 0)) {
                            cipher.login.uris = this.makeUriArray(fieldValue);
                            continue;
                        }
                        else if ((fieldNameLower === "username" || fieldNameLower === "email") &&
                            this.isNullOrWhitespace(cipher.login.username)) {
                            cipher.login.username = fieldValue;
                            continue;
                        }
                        else if (fieldNameLower === "password" &&
                            this.isNullOrWhitespace(cipher.login.password)) {
                            cipher.login.password = fieldValue;
                            continue;
                        }
                        else if (fieldNameLower === "totp" && this.isNullOrWhitespace(cipher.login.totp)) {
                            cipher.login.totp = fieldValue;
                            continue;
                        }
                    }
                    else if (cipher.type === bw_CipherType.Card) {
                        if (fieldNameLower === "cardholder" &&
                            this.isNullOrWhitespace(cipher.card.cardholderName)) {
                            cipher.card.cardholderName = fieldValue;
                            continue;
                        }
                        else if (fieldNameLower === "number" && this.isNullOrWhitespace(cipher.card.number)) {
                            cipher.card.number = fieldValue;
                            cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                            continue;
                        }
                        else if (fieldNameLower === "cvc" && this.isNullOrWhitespace(cipher.card.code)) {
                            cipher.card.code = fieldValue;
                            continue;
                        }
                        else if (fieldNameLower === "expiry date" &&
                            this.isNullOrWhitespace(cipher.card.expMonth) &&
                            this.isNullOrWhitespace(cipher.card.expYear)) {
                            if (this.setCardExpiration(cipher, fieldValue)) {
                                continue;
                            }
                        }
                        else if (fieldNameLower === "type") {
                            // Skip since brand was determined from number above
                            continue;
                        }
                    }
                    this.processKvp(cipher, fieldName, fieldValue);
                }
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
    containsField(fields, name) {
        if (fields == null || name == null) {
            return false;
        }
        return (fields.filter((f) => !this.isNullOrWhitespace(f) && f.toLowerCase() === name.toLowerCase())
            .length > 0);
    }
}

;// ../../libs/importer/src/importers/enpass/enpass-json-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





const bw_androidUrlRegex = new RegExp("androidapp://.*==@", "g");
class bw_EnpassJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || results.items == null || results.items.length === 0) {
            result.success = false;
            return Promise.resolve(result);
        }
        const foldersMap = new Map();
        const foldersIndexMap = new Map();
        const folderTree = this.buildFolderTree(results.folders);
        this.flattenFolderTree(null, folderTree, foldersMap);
        foldersMap.forEach((val, key) => {
            foldersIndexMap.set(key, result.folders.length);
            const f = new bw_FolderView();
            f.name = val;
            result.folders.push(f);
        });
        results.items.forEach((item) => {
            if (item.folders != null && item.folders.length > 0 && foldersIndexMap.has(item.folders[0])) {
                result.folderRelationships.push([
                    result.ciphers.length,
                    foldersIndexMap.get(item.folders[0]),
                ]);
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(item.title);
            cipher.favorite = item.favorite > 0;
            if (item.template_type != null && item.fields != null && item.fields.length > 0) {
                if (item.template_type.indexOf("login.") === 0 ||
                    item.template_type.indexOf("password.") === 0) {
                    this.processLogin(cipher, item.fields);
                }
                else if (item.template_type.indexOf("creditcard.") === 0) {
                    this.processCard(cipher, item.fields);
                }
                else if (item.template_type.indexOf("identity.") < 0 &&
                    item.fields.some((f) => f.type === "password" && !this.isNullOrWhitespace(f.value))) {
                    this.processLogin(cipher, item.fields);
                }
                else {
                    this.processNote(cipher, item.fields);
                }
            }
            cipher.notes += "\n" + this.getValueOrDefault(item.note, "");
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
    processLogin(cipher, fields) {
        const urls = [];
        fields.forEach((field) => {
            if (this.isNullOrWhitespace(field.value) || field.type === "section") {
                return;
            }
            if ((field.type === "username" || field.type === "email") &&
                this.isNullOrWhitespace(cipher.login.username)) {
                cipher.login.username = field.value;
            }
            else if (field.type === "password" && this.isNullOrWhitespace(cipher.login.password)) {
                cipher.login.password = field.value;
            }
            else if (field.type === "totp" && this.isNullOrWhitespace(cipher.login.totp)) {
                cipher.login.totp = field.value;
            }
            else if (field.type === "url") {
                urls.push(field.value);
            }
            else if (field.type === ".Android#") {
                let cleanedValue = field.value.startsWith("androidapp://")
                    ? field.value
                    : "androidapp://" + field.value;
                cleanedValue = cleanedValue.replace("android://", "");
                cleanedValue = cleanedValue.replace(bw_androidUrlRegex, "androidapp://");
                urls.push(cleanedValue);
            }
            else {
                this.processKvp(cipher, field.label, field.value, field.sensitive === 1 ? bw_FieldType.Hidden : bw_FieldType.Text);
            }
        });
        cipher.login.uris = this.makeUriArray(urls);
    }
    processCard(cipher, fields) {
        cipher.card = new bw_CardView();
        cipher.type = bw_CipherType.Card;
        fields.forEach((field) => {
            if (this.isNullOrWhitespace(field.value) ||
                field.type === "section" ||
                field.type === "ccType") {
                return;
            }
            if (field.type === "ccName" && this.isNullOrWhitespace(cipher.card.cardholderName)) {
                cipher.card.cardholderName = field.value;
            }
            else if (field.type === "ccNumber" && this.isNullOrWhitespace(cipher.card.number)) {
                cipher.card.number = field.value;
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
            }
            else if (field.type === "ccCvc" && this.isNullOrWhitespace(cipher.card.code)) {
                cipher.card.code = field.value;
            }
            else if (field.type === "ccExpiry" && this.isNullOrWhitespace(cipher.card.expYear)) {
                if (!this.setCardExpiration(cipher, field.value)) {
                    this.processKvp(cipher, field.label, field.value, field.sensitive === 1 ? bw_FieldType.Hidden : bw_FieldType.Text);
                }
            }
            else {
                this.processKvp(cipher, field.label, field.value, field.sensitive === 1 ? bw_FieldType.Hidden : bw_FieldType.Text);
            }
        });
    }
    processNote(cipher, fields) {
        fields.forEach((field) => {
            if (this.isNullOrWhitespace(field.value) || field.type === "section") {
                return;
            }
            this.processKvp(cipher, field.label, field.value, field.sensitive === 1 ? bw_FieldType.Hidden : bw_FieldType.Text);
        });
    }
    buildFolderTree(folders) {
        if (folders == null) {
            return [];
        }
        const folderTree = [];
        const map = new Map([]);
        folders.forEach((obj) => {
            map.set(obj.uuid, obj);
            obj.children = [];
        });
        folders.forEach((obj) => {
            if (obj.parent_uuid != null && obj.parent_uuid !== "" && map.has(obj.parent_uuid)) {
                map.get(obj.parent_uuid).children.push(obj);
            }
            else {
                folderTree.push(obj);
            }
        });
        return folderTree;
    }
    flattenFolderTree(titlePrefix, tree, map) {
        if (tree == null) {
            return;
        }
        tree.forEach((f) => {
            if (f.title != null && f.title.trim() !== "") {
                let title = f.title.trim();
                if (titlePrefix != null && titlePrefix.trim() !== "") {
                    title = titlePrefix + "/" + title;
                }
                map.set(f.uuid, title);
                if (f.children != null && f.children.length !== 0) {
                    this.flattenFolderTree(title, f.children, map);
                }
            }
        });
    }
}

;// ../../libs/importer/src/importers/enpass/index.ts



;// ../../libs/importer/src/importers/firefox-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_FirefoxCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results
            .filter((value) => {
            return value.url !== "chrome://FirefoxAccounts";
        })
            .forEach((value) => {
            const cipher = this.initLoginCipher();
            const url = this.getValueOrDefault(value.url, this.getValueOrDefault(value.hostname));
            cipher.name = this.getValueOrDefault(this.nameFromUrl(url), "--");
            cipher.login.username = this.getValueOrDefault(value.username);
            cipher.login.password = this.getValueOrDefault(value.password);
            cipher.login.uris = this.makeUriArray(url);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/fsecure/fsecure-fsk-types.ts
var bw_FskEntryTypesEnum;
(function (FskEntryTypesEnum) {
    FskEntryTypesEnum[FskEntryTypesEnum["Login"] = 1] = "Login";
    FskEntryTypesEnum[FskEntryTypesEnum["CreditCard"] = 2] = "CreditCard";
})(bw_FskEntryTypesEnum || (bw_FskEntryTypesEnum = {}));

;// ../../libs/importer/src/importers/fsecure/fsecure-fsk-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_FSecureFskImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || results.data == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        for (const key in results.data) {
            // eslint-disable-next-line
            if (!results.data.hasOwnProperty(key)) {
                continue;
            }
            const value = results.data[key];
            const cipher = this.parseEntry(value);
            result.ciphers.push(cipher);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    parseEntry(entry) {
        const cipher = this.initLoginCipher();
        cipher.name = this.getValueOrDefault(entry.service);
        cipher.notes = this.getValueOrDefault(entry.notes);
        cipher.favorite = entry.favorite > 0;
        switch (entry.type) {
            case bw_FskEntryTypesEnum.Login:
                this.handleLoginEntry(entry, cipher);
                break;
            case bw_FskEntryTypesEnum.CreditCard:
                this.handleCreditCardEntry(entry, cipher);
                break;
            default:
                return;
                break;
        }
        this.convertToNoteIfNeeded(cipher);
        this.cleanupCipher(cipher);
        return cipher;
    }
    handleLoginEntry(entry, cipher) {
        cipher.login.username = this.getValueOrDefault(entry.username);
        cipher.login.password = this.getValueOrDefault(entry.password);
        cipher.login.uris = this.makeUriArray(entry.url);
    }
    handleCreditCardEntry(entry, cipher) {
        cipher.type = bw_CipherType.Card;
        cipher.card = new bw_CardView();
        cipher.card.cardholderName = this.getValueOrDefault(entry.username);
        cipher.card.number = this.getValueOrDefault(entry.creditNumber);
        cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
        cipher.card.code = this.getValueOrDefault(entry.creditCvv);
        if (!this.isNullOrWhitespace(entry.creditExpiry)) {
            if (!this.setCardExpiration(cipher, entry.creditExpiry)) {
                this.processKvp(cipher, "Expiration", entry.creditExpiry);
            }
        }
        if (!this.isNullOrWhitespace(entry.password)) {
            this.processKvp(cipher, "PIN", entry.password);
        }
    }
}

;// ../../libs/importer/src/importers/gnome-json-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_GnomeJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || Object.keys(results).length === 0) {
            result.success = false;
            return Promise.resolve(result);
        }
        for (const keyRing in results) {
            if (!results.hasOwnProperty(keyRing) || // eslint-disable-line
                this.isNullOrWhitespace(keyRing) ||
                results[keyRing].length === 0) {
                continue;
            }
            results[keyRing].forEach((value) => {
                if (this.isNullOrWhitespace(value.display_name) ||
                    value.display_name.indexOf("http") !== 0) {
                    return;
                }
                this.processFolder(result, keyRing);
                const cipher = this.initLoginCipher();
                cipher.name = value.display_name.replace("http://", "").replace("https://", "");
                if (cipher.name.length > 30) {
                    cipher.name = cipher.name.substring(0, 30);
                }
                cipher.login.password = this.getValueOrDefault(value.secret);
                cipher.login.uris = this.makeUriArray(value.display_name);
                if (value.attributes != null) {
                    cipher.login.username =
                        value.attributes != null
                            ? this.getValueOrDefault(value.attributes.username_value)
                            : null;
                    for (const attr in value.attributes) {
                        if (!value.attributes.hasOwnProperty(attr) || // eslint-disable-line
                            attr === "username_value" ||
                            attr === "xdg:schema") {
                            continue;
                        }
                        this.processKvp(cipher, attr, value.attributes[attr]);
                    }
                }
                this.convertToNoteIfNeeded(cipher);
                this.cleanupCipher(cipher);
                result.ciphers.push(cipher);
            });
        }
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/kaspersky-txt-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


const bw_NotesHeader = "Notes\n\n";
const bw_ApplicationsHeader = "Applications\n\n";
const bw_WebsitesHeader = "Websites\n\n";
const bw_Delimiter = "\n---\n";
class bw_KasperskyTxtImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        let notesData;
        let applicationsData;
        let websitesData;
        let workingData = this.splitNewLine(data).join("\n");
        if (workingData.indexOf(bw_NotesHeader) !== -1) {
            const parts = workingData.split(bw_NotesHeader);
            if (parts.length > 1) {
                workingData = parts[0];
                notesData = parts[1];
            }
        }
        if (workingData.indexOf(bw_ApplicationsHeader) !== -1) {
            const parts = workingData.split(bw_ApplicationsHeader);
            if (parts.length > 1) {
                workingData = parts[0];
                applicationsData = parts[1];
            }
        }
        if (workingData.indexOf(bw_WebsitesHeader) === 0) {
            const parts = workingData.split(bw_WebsitesHeader);
            if (parts.length > 1) {
                workingData = parts[0];
                websitesData = parts[1];
            }
        }
        const notes = this.parseDataCategory(notesData);
        const applications = this.parseDataCategory(applicationsData);
        const websites = this.parseDataCategory(websitesData);
        notes.forEach((n) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(n.get("Name"));
            cipher.notes = this.getValueOrDefault(n.get("Text"));
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        websites.concat(applications).forEach((w) => {
            const cipher = this.initLoginCipher();
            const nameKey = w.has("Website name") ? "Website name" : "Application";
            cipher.name = this.getValueOrDefault(w.get(nameKey), "");
            if (!this.isNullOrWhitespace(w.get("Login name"))) {
                if (!this.isNullOrWhitespace(cipher.name)) {
                    cipher.name += ": ";
                }
                cipher.name += w.get("Login name");
            }
            cipher.notes = this.getValueOrDefault(w.get("Comment"));
            if (w.has("Website URL")) {
                cipher.login.uris = this.makeUriArray(w.get("Website URL"));
            }
            cipher.login.username = this.getValueOrDefault(w.get("Login"));
            cipher.login.password = this.getValueOrDefault(w.get("Password"));
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
    parseDataCategory(data) {
        if (this.isNullOrWhitespace(data) || data.indexOf(bw_Delimiter) === -1) {
            return [];
        }
        const items = [];
        data.split(bw_Delimiter).forEach((p) => {
            if (p.indexOf("\n") === -1) {
                return;
            }
            const item = new Map();
            let itemComment;
            let itemCommentKey;
            p.split("\n").forEach((l) => {
                if (itemComment != null) {
                    itemComment += "\n" + l;
                    return;
                }
                const colonIndex = l.indexOf(":");
                let key;
                let val;
                if (colonIndex === -1) {
                    return;
                }
                else {
                    key = l.substring(0, colonIndex);
                    if (l.length > colonIndex + 1) {
                        val = l.substring(colonIndex + 2);
                    }
                }
                if (key != null) {
                    item.set(key, val);
                }
                if (key === "Comment" || key === "Text") {
                    itemComment = val;
                    itemCommentKey = key;
                }
            });
            if (itemComment != null && itemCommentKey != null) {
                item.set(itemCommentKey, itemComment);
            }
            if (item.size === 0) {
                return;
            }
            items.push(item);
        });
        return items;
    }
}

;// ../../libs/importer/src/importers/keepass2-xml-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_KeePass2XmlImporter extends bw_base_importer_BaseImporter {
    constructor() {
        super(...arguments);
        this.result = new bw_import_result_ImportResult();
    }
    parse(data) {
        const doc = this.parseXml(data);
        if (doc == null) {
            this.result.success = false;
            return Promise.resolve(this.result);
        }
        //Note: The doc.querySelector("KeePassFile > Root > Group") no longers works on node and we have to breakdown the query by nodes
        const KeePassFileNode = doc.querySelector("KeePassFile");
        if (KeePassFileNode == null) {
            this.result.errorMessage = "Missing `KeePassFile` node.";
            this.result.success = false;
            return Promise.resolve(this.result);
        }
        const RootNode = KeePassFileNode.querySelector("Root");
        if (RootNode == null) {
            this.result.errorMessage = "Missing `KeePassFile > Root` node.";
            this.result.success = false;
            return Promise.resolve(this.result);
        }
        const rootGroup = RootNode.querySelector("Group");
        if (rootGroup == null) {
            this.result.errorMessage = "Missing `KeePassFile > Root > Group` node.";
            this.result.success = false;
            return Promise.resolve(this.result);
        }
        this.traverse(rootGroup, true, "");
        if (this.organization) {
            this.moveFoldersToCollections(this.result);
        }
        this.result.success = true;
        return Promise.resolve(this.result);
    }
    traverse(node, isRootNode, groupPrefixName) {
        const folderIndex = this.result.folders.length;
        let groupName = groupPrefixName;
        if (!isRootNode) {
            if (groupName !== "") {
                groupName += "/";
            }
            const nameEl = this.querySelectorDirectChild(node, "Name");
            groupName += nameEl == null ? "-" : nameEl.textContent;
            const folder = new bw_FolderView();
            folder.name = groupName;
            this.result.folders.push(folder);
        }
        this.querySelectorAllDirectChild(node, "Entry").forEach((entry) => {
            const cipherIndex = this.result.ciphers.length;
            const cipher = this.initLoginCipher();
            this.querySelectorAllDirectChild(entry, "String").forEach((entryString) => {
                const valueEl = this.querySelectorDirectChild(entryString, "Value");
                const value = valueEl != null ? valueEl.textContent : null;
                if (this.isNullOrWhitespace(value)) {
                    return;
                }
                const keyEl = this.querySelectorDirectChild(entryString, "Key");
                const key = keyEl != null ? keyEl.textContent : null;
                if (key === "URL") {
                    cipher.login.uris = this.makeUriArray(value);
                }
                else if (key === "UserName") {
                    cipher.login.username = value;
                }
                else if (key === "Password") {
                    cipher.login.password = value;
                }
                else if (key === "otp") {
                    cipher.login.totp = value.replace("key=", "");
                }
                else if (key === "Title") {
                    cipher.name = value;
                }
                else if (key === "Notes") {
                    cipher.notes += value + "\n";
                }
                else {
                    let type = bw_FieldType.Text;
                    const attrs = valueEl.attributes;
                    if (attrs.length > 0 &&
                        attrs.ProtectInMemory != null &&
                        attrs.ProtectInMemory.value === "True") {
                        type = bw_FieldType.Hidden;
                    }
                    this.processKvp(cipher, key, value, type);
                }
            });
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
            if (!isRootNode) {
                this.result.folderRelationships.push([cipherIndex, folderIndex]);
            }
        });
        this.querySelectorAllDirectChild(node, "Group").forEach((group) => {
            this.traverse(group, false, groupName);
        });
    }
}

;// ../../libs/importer/src/importers/keepassx-csv-importer.ts


class bw_KeePassXCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (this.isNullOrWhitespace(value.Title)) {
                return;
            }
            value.Group =
                !this.isNullOrWhitespace(value.Group) && value.Group.startsWith("Root/")
                    ? value.Group.replace("Root/", "")
                    : value.Group;
            const groupName = !this.isNullOrWhitespace(value.Group) ? value.Group : null;
            this.processFolder(result, groupName);
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValueOrDefault(value.Notes);
            cipher.name = this.getValueOrDefault(value.Title, "--");
            cipher.login.username = this.getValueOrDefault(value.Username);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.uris = this.makeUriArray(value.URL);
            cipher.login.totp = this.getValueOrDefault(value.TOTP);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/keeper/keeper-csv-importer.ts


class bw_KeeperCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length < 6) {
                return;
            }
            this.processFolder(result, value[0]);
            const cipher = this.initLoginCipher();
            const notes = this.getValueOrDefault(value[5]);
            if (notes) {
                cipher.notes = `${notes}\n`;
            }
            cipher.name = this.getValueOrDefault(value[1], "--");
            cipher.login.username = this.getValueOrDefault(value[2]);
            cipher.login.password = this.getValueOrDefault(value[3]);
            cipher.login.uris = this.makeUriArray(value[4]);
            if (value.length > 7) {
                // we have some custom fields.
                for (let i = 7; i < value.length; i = i + 2) {
                    if (value[i] == "TFC:Keeper") {
                        cipher.login.totp = value[i + 1];
                    }
                    else {
                        this.processKvp(cipher, value[i], value[i + 1]);
                    }
                }
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/keeper/keeper-json-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_KeeperJsonImporter extends (/* unused pure expression or super */ null && (BaseImporter)) {
    parse(data) {
        const result = new ImportResult();
        const keeperExport = JSON.parse(data);
        if (keeperExport == null || keeperExport.records == null || keeperExport.records.length === 0) {
            result.success = false;
            return Promise.resolve(result);
        }
        keeperExport.records.forEach((record) => {
            this.parseFolders(result, record);
            const cipher = this.initLoginCipher();
            cipher.name = record.title;
            cipher.login.username = record.login;
            cipher.login.password = record.password;
            cipher.login.uris = this.makeUriArray(record.login_url);
            cipher.notes = record.notes;
            if (record.custom_fields != null) {
                let customfieldKeys = Object.keys(record.custom_fields);
                if (record.custom_fields["TFC:Keeper"] != null) {
                    customfieldKeys = customfieldKeys.filter((item) => item !== "TFC:Keeper");
                    cipher.login.totp = record.custom_fields["TFC:Keeper"];
                }
                customfieldKeys.forEach((key) => {
                    this.processKvp(cipher, key, record.custom_fields[key]);
                });
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    parseFolders(result, record) {
        if (record.folders == null || record.folders.length === 0) {
            return;
        }
        record.folders.forEach((item) => {
            if (item.folder != null) {
                this.processFolder(result, item.folder);
                return;
            }
            if (item.shared_folder != null) {
                this.processFolder(result, item.shared_folder);
                return;
            }
        });
    }
}

;// ../../libs/importer/src/importers/keeper/index.ts



;// ../../libs/importer/src/importers/lastpass/lastpass-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore









class bw_LastPassCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipherIndex = result.ciphers.length;
            let folderIndex = result.folders.length;
            let grouping = value.grouping;
            if (grouping != null) {
                // eslint-disable-next-line
                grouping = grouping.replace(/\\/g, "/").replace(/[\x00-\x1F\x7F-\x9F]/g, "");
            }
            const hasFolder = this.getValueOrDefault(grouping, "(none)") !== "(none)";
            let addFolder = hasFolder;
            if (hasFolder) {
                for (let i = 0; i < result.folders.length; i++) {
                    if (result.folders[i].name === grouping) {
                        addFolder = false;
                        folderIndex = i;
                        break;
                    }
                }
            }
            const cipher = this.buildBaseCipher(value);
            if (cipher.type === bw_CipherType.Login) {
                cipher.notes = this.getValueOrDefault(value.extra);
                cipher.login = new bw_LoginView();
                cipher.login.uris = this.makeUriArray(value.url);
                cipher.login.username = this.getValueOrDefault(value.username);
                cipher.login.password = this.getValueOrDefault(value.password);
                cipher.login.totp = this.getValueOrDefault(value.totp);
            }
            else if (cipher.type === bw_CipherType.SecureNote) {
                this.parseSecureNote(value, cipher);
            }
            else if (cipher.type === bw_CipherType.Card) {
                cipher.card = this.parseCard(value);
                cipher.notes = this.getValueOrDefault(value.notes);
            }
            else if (cipher.type === bw_CipherType.Identity) {
                cipher.identity = this.parseIdentity(value);
                cipher.notes = this.getValueOrDefault(value.notes);
                if (!this.isNullOrWhitespace(value.ccnum)) {
                    // there is a card on this identity too
                    const cardCipher = this.buildBaseCipher(value);
                    cardCipher.identity = null;
                    cardCipher.type = bw_CipherType.Card;
                    cardCipher.card = this.parseCard(value);
                    result.ciphers.push(cardCipher);
                }
            }
            result.ciphers.push(cipher);
            if (addFolder) {
                const f = new bw_FolderView();
                f.name = grouping;
                result.folders.push(f);
            }
            if (hasFolder) {
                result.folderRelationships.push([cipherIndex, folderIndex]);
            }
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    buildBaseCipher(value) {
        const cipher = new bw_CipherView();
        // eslint-disable-next-line
        if (value.hasOwnProperty("profilename") && value.hasOwnProperty("profilelanguage")) {
            // form fill
            cipher.favorite = false;
            cipher.name = this.getValueOrDefault(value.profilename, "--");
            cipher.type = bw_CipherType.Card;
            if (!this.isNullOrWhitespace(value.title) ||
                !this.isNullOrWhitespace(value.firstname) ||
                !this.isNullOrWhitespace(value.lastname) ||
                !this.isNullOrWhitespace(value.address1) ||
                !this.isNullOrWhitespace(value.phone) ||
                !this.isNullOrWhitespace(value.username) ||
                !this.isNullOrWhitespace(value.email)) {
                cipher.type = bw_CipherType.Identity;
            }
        }
        else {
            // site or secure note
            cipher.favorite = !this.organization && this.getValueOrDefault(value.fav, "0") === "1";
            cipher.name = this.getValueOrDefault(value.name, "--");
            cipher.type = value.url === "http://sn" ? bw_CipherType.SecureNote : bw_CipherType.Login;
        }
        return cipher;
    }
    parseCard(value) {
        const card = new bw_CardView();
        card.cardholderName = this.getValueOrDefault(value.ccname);
        card.number = this.getValueOrDefault(value.ccnum);
        card.code = this.getValueOrDefault(value.cccsc);
        card.brand = bw_CardView.getCardBrandByPatterns(card.number);
        if (!this.isNullOrWhitespace(value.ccexp) && value.ccexp.indexOf("-") > -1) {
            const ccexpParts = value.ccexp.split("-");
            if (ccexpParts.length > 1) {
                card.expYear = ccexpParts[0];
                card.expMonth = ccexpParts[1];
                if (card.expMonth.length === 2 && card.expMonth[0] === "0") {
                    card.expMonth = card.expMonth[1];
                }
            }
        }
        return card;
    }
    parseIdentity(value) {
        const identity = new bw_IdentityView();
        identity.title = this.getValueOrDefault(value.title);
        identity.firstName = this.getValueOrDefault(value.firstname);
        identity.middleName = this.getValueOrDefault(value.middlename);
        identity.lastName = this.getValueOrDefault(value.lastname);
        identity.username = this.getValueOrDefault(value.username);
        identity.company = this.getValueOrDefault(value.company);
        identity.ssn = this.getValueOrDefault(value.ssn);
        identity.address1 = this.getValueOrDefault(value.address1);
        identity.address2 = this.getValueOrDefault(value.address2);
        identity.address3 = this.getValueOrDefault(value.address3);
        identity.city = this.getValueOrDefault(value.city);
        identity.state = this.getValueOrDefault(value.state);
        identity.postalCode = this.getValueOrDefault(value.zip);
        identity.country = this.getValueOrDefault(value.country);
        identity.email = this.getValueOrDefault(value.email);
        identity.phone = this.getValueOrDefault(value.phone);
        if (!this.isNullOrWhitespace(identity.title)) {
            identity.title = identity.title.charAt(0).toUpperCase() + identity.title.slice(1);
        }
        return identity;
    }
    parseSecureNote(value, cipher) {
        const extraParts = this.splitNewLine(value.extra);
        let processedNote = false;
        if (extraParts.length) {
            const typeParts = extraParts[0].split(":");
            if (typeParts.length > 1 &&
                typeParts[0] === "NoteType" &&
                (typeParts[1] === "Credit Card" || typeParts[1] === "Address")) {
                if (typeParts[1] === "Credit Card") {
                    const mappedData = this.parseSecureNoteMapping(cipher, extraParts, {
                        Number: "number",
                        "Name on Card": "cardholderName",
                        "Security Code": "code",
                        // LP provides date in a format like 'June,2020'
                        // Store in expMonth, then parse and modify
                        "Expiration Date": "expMonth",
                    });
                    if (this.isNullOrWhitespace(mappedData.expMonth) || mappedData.expMonth === ",") {
                        // No expiration data
                        mappedData.expMonth = undefined;
                    }
                    else {
                        const [monthString, year] = mappedData.expMonth.split(",");
                        // Parse month name into number
                        if (!this.isNullOrWhitespace(monthString)) {
                            const month = new Date(Date.parse(monthString.trim() + " 1, 2012")).getMonth() + 1;
                            if (isNaN(month)) {
                                mappedData.expMonth = undefined;
                            }
                            else {
                                mappedData.expMonth = month.toString();
                            }
                        }
                        else {
                            mappedData.expMonth = undefined;
                        }
                        if (!this.isNullOrWhitespace(year)) {
                            mappedData.expYear = year;
                        }
                    }
                    cipher.type = bw_CipherType.Card;
                    cipher.card = mappedData;
                }
                else if (typeParts[1] === "Address") {
                    const mappedData = this.parseSecureNoteMapping(cipher, extraParts, {
                        Title: "title",
                        "First Name": "firstName",
                        "Last Name": "lastName",
                        "Middle Name": "middleName",
                        Company: "company",
                        "Address 1": "address1",
                        "Address 2": "address2",
                        "Address 3": "address3",
                        "City / Town": "city",
                        State: "state",
                        "Zip / Postal Code": "postalCode",
                        Country: "country",
                        "Email Address": "email",
                        Username: "username",
                    });
                    cipher.type = bw_CipherType.Identity;
                    cipher.identity = mappedData;
                }
                processedNote = true;
            }
        }
        if (!processedNote) {
            cipher.secureNote = new bw_SecureNoteView();
            cipher.secureNote.type = bw_SecureNoteType.Generic;
            cipher.notes = this.getValueOrDefault(value.extra);
        }
    }
    parseSecureNoteMapping(cipher, extraParts, map) {
        const dataObj = {};
        let processingNotes = false;
        extraParts.forEach((extraPart) => {
            let key = null;
            let val = null;
            if (!processingNotes) {
                if (this.isNullOrWhitespace(extraPart)) {
                    return;
                }
                const colonIndex = extraPart.indexOf(":");
                if (colonIndex === -1) {
                    key = extraPart;
                }
                else {
                    key = extraPart.substring(0, colonIndex);
                    if (extraPart.length > colonIndex) {
                        val = extraPart.substring(colonIndex + 1);
                    }
                }
                if (this.isNullOrWhitespace(key) || this.isNullOrWhitespace(val) || key === "NoteType") {
                    return;
                }
            }
            if (processingNotes) {
                cipher.notes += "\n" + extraPart;
            }
            else if (key === "Notes") {
                if (!this.isNullOrWhitespace(cipher.notes)) {
                    cipher.notes += "\n" + val;
                }
                else {
                    cipher.notes = val;
                }
                processingNotes = true;
                // eslint-disable-next-line
            }
            else if (map.hasOwnProperty(key)) {
                dataObj[map[key]] = val;
            }
            else {
                this.processKvp(cipher, key, val);
            }
        });
        return dataObj;
    }
}

;// ../../libs/importer/src/importers/lastpass/index.ts


;// ../../libs/importer/src/importers/logmeonce-csv-importer.ts


class bw_LogMeOnceCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length < 4) {
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value[0], "--");
            cipher.login.username = this.getValueOrDefault(value[2]);
            cipher.login.password = this.getValueOrDefault(value[3]);
            cipher.login.uris = this.makeUriArray(value[1]);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/meldium-csv-importer.ts


class bw_MeldiumCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.DisplayName, "--");
            cipher.notes = this.getValueOrDefault(value.Notes);
            cipher.login.username = this.getValueOrDefault(value.UserName);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.uris = this.makeUriArray(value.Url);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/msecure-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_MSecureCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false, { delimiter: "," });
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length < 3) {
                return;
            }
            const folderName = this.getValueOrDefault(value[2], "Unassigned") !== "Unassigned" ? value[2] : null;
            this.processFolder(result, folderName);
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value[0].split("|")[0], "--");
            if (value[1] === "Web Logins" || value[1] === "Login") {
                cipher.login.username = this.getValueOrDefault(this.splitValueRetainingLastPart(value[5]));
                cipher.login.uris = this.makeUriArray(this.splitValueRetainingLastPart(value[4]));
                cipher.login.password = this.getValueOrDefault(this.splitValueRetainingLastPart(value[6]));
                cipher.notes = !this.isNullOrWhitespace(value[3]) ? value[3].split("\\n").join("\n") : null;
            }
            else if (value[1] === "Credit Card") {
                cipher.type = bw_CipherType.Card;
                cipher.card.number = this.getValueOrDefault(this.splitValueRetainingLastPart(value[4]));
                const [month, year] = this.getValueOrDefault(this.splitValueRetainingLastPart(value[5])).split("/");
                cipher.card.expMonth = month.trim();
                cipher.card.expYear = year.trim();
                const securityCodeRegex = RegExp("^Security Code\\|\\d*\\|");
                const securityCodeEntry = value.find((entry) => securityCodeRegex.test(entry));
                cipher.card.code = this.getValueOrDefault(this.splitValueRetainingLastPart(securityCodeEntry));
                const cardNameRegex = RegExp("^Name on Card\\|\\d*\\|");
                const nameOnCardEntry = value.find((entry) => entry.match(cardNameRegex));
                cipher.card.cardholderName = this.getValueOrDefault(this.splitValueRetainingLastPart(nameOnCardEntry));
                cipher.card.brand = this.getValueOrDefault(this.splitValueRetainingLastPart(value[9]), "");
                const noteRegex = RegExp("\\|\\d*\\|");
                const rawNotes = value
                    .slice(2)
                    .filter((entry) => !this.isNullOrWhitespace(entry) && !noteRegex.test(entry));
                const noteIndexes = [8, 10, 11];
                const indexedNotes = noteIndexes
                    .filter((idx) => value[idx] && noteRegex.test(value[idx]))
                    .map((idx) => value[idx])
                    .map((val) => {
                    const key = val.split("|")[0];
                    const value = this.getValueOrDefault(this.splitValueRetainingLastPart(val), "");
                    return `${key}: ${value}`;
                });
                cipher.notes = [...rawNotes, ...indexedNotes].join("\n");
            }
            else if (value.length > 3) {
                cipher.type = bw_CipherType.SecureNote;
                cipher.secureNote = new bw_SecureNoteView();
                cipher.secureNote.type = bw_SecureNoteType.Generic;
                for (let i = 3; i < value.length; i++) {
                    if (!this.isNullOrWhitespace(value[i])) {
                        cipher.notes += value[i] + "\n";
                    }
                }
            }
            if (!this.isNullOrWhitespace(value[1]) &&
                cipher.type !== bw_CipherType.Login &&
                cipher.type !== bw_CipherType.Card) {
                cipher.name = value[1] + ": " + cipher.name;
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    // mSecure returns values separated by "|" where after the second separator is the value
    // like "Password|8|myPassword", we want to keep the "myPassword" but also ensure that if
    // the value contains any "|" it works fine
    splitValueRetainingLastPart(value) {
        return value && value.split("|").slice(0, 2).concat(value.split("|").slice(2).join("|")).pop();
    }
}

;// ../../libs/importer/src/importers/myki-csv-importer.ts






const bw_mappedBaseColumns = ["nickname", "additionalInfo"];
const bw_mappedUserAccountColumns = new Set(bw_mappedBaseColumns.concat(["url", "username", "password", "twofaSecret"]));
const bw_mappedCreditCardColumns = new Set(bw_mappedBaseColumns.concat(["cardNumber", "cardName", "exp_month", "exp_year", "cvv"]));
const bw_mappedIdentityColumns = new Set(bw_mappedBaseColumns.concat([
    "title",
    "firstName",
    "middleName",
    "lastName",
    "email",
    "firstAddressLine",
    "secondAddressLine",
    "city",
    "country",
    "zipCode",
]));
const bw_mappedIdCardColumns = new Set(bw_mappedBaseColumns.concat(["idName", "idNumber", "idCountry"]));
const bw_mappedTwoFaColumns = new Set(bw_mappedBaseColumns.concat(["authToken"]));
const bw_mappedUserNoteColumns = new Set(bw_mappedBaseColumns.concat(["content"]));
class bw_MykiCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.nickname, "--");
            cipher.notes = this.getValueOrDefault(value.additionalInfo);
            if (value.url !== undefined) {
                // Accounts
                cipher.login.uris = this.makeUriArray(value.url);
                cipher.login.username = this.getValueOrDefault(value.username);
                cipher.login.password = this.getValueOrDefault(value.password);
                cipher.login.totp = this.getValueOrDefault(value.twofaSecret);
                this.importUnmappedFields(cipher, value, bw_mappedUserAccountColumns);
            }
            else if (value.authToken !== undefined) {
                // TwoFA
                cipher.login.totp = this.getValueOrDefault(value.authToken);
                this.importUnmappedFields(cipher, value, bw_mappedTwoFaColumns);
            }
            else if (value.cardNumber !== undefined) {
                // Cards
                cipher.card = new bw_CardView();
                cipher.type = bw_CipherType.Card;
                cipher.card.cardholderName = this.getValueOrDefault(value.cardName);
                cipher.card.number = this.getValueOrDefault(value.cardNumber);
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                cipher.card.expMonth = this.getValueOrDefault(value.exp_month);
                cipher.card.expYear = this.getValueOrDefault(value.exp_year);
                cipher.card.code = this.getValueOrDefault(value.cvv);
                this.importUnmappedFields(cipher, value, bw_mappedCreditCardColumns);
            }
            else if (value.firstName !== undefined) {
                // Identities
                cipher.identity = new bw_IdentityView();
                cipher.type = bw_CipherType.Identity;
                cipher.identity.title = this.getValueOrDefault(value.title);
                cipher.identity.firstName = this.getValueOrDefault(value.firstName);
                cipher.identity.middleName = this.getValueOrDefault(value.middleName);
                cipher.identity.lastName = this.getValueOrDefault(value.lastName);
                cipher.identity.phone = this.getValueOrDefault(value.number);
                cipher.identity.email = this.getValueOrDefault(value.email);
                cipher.identity.address1 = this.getValueOrDefault(value.firstAddressLine);
                cipher.identity.address2 = this.getValueOrDefault(value.secondAddressLine);
                cipher.identity.city = this.getValueOrDefault(value.city);
                cipher.identity.country = this.getValueOrDefault(value.country);
                cipher.identity.postalCode = this.getValueOrDefault(value.zipCode);
                this.importUnmappedFields(cipher, value, bw_mappedIdentityColumns);
            }
            else if (value.idType !== undefined) {
                // IdCards
                cipher.identity = new bw_IdentityView();
                cipher.type = bw_CipherType.Identity;
                this.processFullName(cipher, value.idName);
                cipher.identity.country = this.getValueOrDefault(value.idCountry);
                switch (value.idType) {
                    // case "Driver's License":
                    // case "ID Card":
                    // case "Outdoor License":
                    // case "Software License":
                    // case "Tax Number":
                    // case "Bank Account":
                    // case "Insurance Card":
                    // case "Health Card":
                    // case "Membership":
                    // case "Database":
                    // case "Reward Program":
                    // case "Tour Visa":
                    case "Passport":
                        cipher.identity.passportNumber = value.idNumber;
                        break;
                    case "Social Security":
                        cipher.identity.ssn = value.idNumber;
                        break;
                    default:
                        cipher.identity.licenseNumber = value.idNumber;
                        break;
                }
                this.importUnmappedFields(cipher, value, bw_mappedIdCardColumns);
            }
            else if (value.content !== undefined) {
                // Notes
                cipher.secureNote = new bw_SecureNoteView();
                cipher.type = bw_CipherType.SecureNote;
                cipher.secureNote.type = bw_SecureNoteType.Generic;
                cipher.notes = this.getValueOrDefault(value.content);
                this.importUnmappedFields(cipher, value, bw_mappedUserNoteColumns);
            }
            else {
                return;
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
    importUnmappedFields(cipher, row, mappedValues) {
        const unmappedFields = Object.keys(row).filter((x) => !mappedValues.has(x));
        unmappedFields.forEach((key) => {
            const item = row;
            this.processKvp(cipher, key, item[key]);
        });
    }
}

;// ../../libs/importer/src/importers/netwrix/netwrix-passwordsecure-csv-importer.ts


const bw_mappedColumns = new Set([
    "Organisationseinheit",
    "Informationen",
    "Beschreibung",
    "Benutzername",
    "Passwort",
    "Internetseite",
    "One-Time Passwort",
]);
/**
 * Importer for Netwrix Password Secure CSV files.
 * @see https://www.netwrix.com/enterprise_password_management_software.html
 */
class bw_NetwrixPasswordSecureCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((row) => {
            this.processFolder(result, row.Organisationseinheit);
            const cipher = this.initLoginCipher();
            const notes = this.getValueOrDefault(row.Informationen);
            if (notes) {
                cipher.notes = `${notes}\n`;
            }
            cipher.name = this.getValueOrDefault(row.Beschreibung, "--");
            cipher.login.username = this.getValueOrDefault(row.Benutzername);
            cipher.login.password = this.getValueOrDefault(row.Passwort);
            cipher.login.uris = this.makeUriArray(row.Internetseite);
            cipher.login.totp = this.getValueOrDefault(row["One-Time Passwort"]);
            this.importUnmappedFields(cipher, row, bw_mappedColumns);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    importUnmappedFields(cipher, row, mappedValues) {
        const unmappedFields = Object.keys(row).filter((x) => !mappedValues.has(x));
        unmappedFields.forEach((key) => {
            const item = row;
            this.processKvp(cipher, key, item[key]);
        });
    }
}

;// ../../libs/importer/src/importers/netwrix/index.ts


;// ../../libs/importer/src/importers/nordpass-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






class bw_NordPassCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((record) => {
            const recordType = this.evaluateType(record);
            if (recordType === undefined) {
                return;
            }
            this.processFolder(result, record.folder);
            const cipher = new bw_CipherView();
            cipher.name = this.getValueOrDefault(record.name, "--");
            cipher.notes = this.getValueOrDefault(record.note);
            if (record.custom_fields) {
                const customFieldsParsed = JSON.parse(record.custom_fields);
                if (customFieldsParsed && customFieldsParsed.length > 0) {
                    customFieldsParsed.forEach((field) => {
                        let fieldType = bw_FieldType.Text;
                        if (field.type == "hidden") {
                            fieldType = bw_FieldType.Hidden;
                        }
                        this.processKvp(cipher, field.label, field.value, fieldType);
                    });
                }
            }
            switch (recordType) {
                case bw_CipherType.Login:
                    cipher.type = bw_CipherType.Login;
                    cipher.login = new bw_LoginView();
                    cipher.login.username = this.getValueOrDefault(record.username);
                    cipher.login.password = this.getValueOrDefault(record.password);
                    if (record.additional_urls) {
                        const additionalUrlsParsed = JSON.parse(record.additional_urls);
                        const uris = [record.url, ...additionalUrlsParsed];
                        cipher.login.uris = this.makeUriArray(uris);
                    }
                    else {
                        cipher.login.uris = this.makeUriArray(record.url);
                    }
                    break;
                case bw_CipherType.Card:
                    cipher.type = bw_CipherType.Card;
                    cipher.card.cardholderName = this.getValueOrDefault(record.cardholdername);
                    cipher.card.number = this.getValueOrDefault(record.cardnumber);
                    cipher.card.code = this.getValueOrDefault(record.cvc);
                    cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                    this.setCardExpiration(cipher, record.expirydate);
                    break;
                case bw_CipherType.Identity:
                    cipher.type = bw_CipherType.Identity;
                    this.processFullName(cipher, this.getValueOrDefault(record.full_name));
                    cipher.identity.address1 = this.getValueOrDefault(record.address1);
                    cipher.identity.address2 = this.getValueOrDefault(record.address2);
                    cipher.identity.city = this.getValueOrDefault(record.city);
                    cipher.identity.state = this.getValueOrDefault(record.state);
                    cipher.identity.postalCode = this.getValueOrDefault(record.zipcode);
                    cipher.identity.country = this.getValueOrDefault(record.country);
                    if (cipher.identity.country != null) {
                        cipher.identity.country = cipher.identity.country.toUpperCase();
                    }
                    cipher.identity.email = this.getValueOrDefault(record.email);
                    cipher.identity.phone = this.getValueOrDefault(record.phone_number);
                    break;
                case bw_CipherType.SecureNote:
                    cipher.type = bw_CipherType.SecureNote;
                    cipher.secureNote.type = bw_SecureNoteType.Generic;
                    break;
                default:
                    break;
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    evaluateType(record) {
        switch (record.type) {
            case "password":
                return bw_CipherType.Login;
            case "credit_card":
                return bw_CipherType.Card;
            case "note":
                return bw_CipherType.SecureNote;
            case "identity":
                return bw_CipherType.Identity;
        }
        return undefined;
    }
}

;// ../../libs/importer/src/importers/onepassword/onepassword-1pif-importer.ts







class bw_OnePassword1PifImporter extends bw_base_importer_BaseImporter {
    constructor() {
        super(...arguments);
        this.result = new bw_import_result_ImportResult();
    }
    parse(data) {
        data.split(this.newLineRegex).forEach((line) => {
            if (this.isNullOrWhitespace(line) || line[0] !== "{") {
                return;
            }
            const item = JSON.parse(line);
            if (item.trashed === true) {
                return;
            }
            const cipher = this.initLoginCipher();
            if (this.isNullOrWhitespace(item.hmac)) {
                this.processStandardItem(item, cipher);
            }
            else {
                this.processWinOpVaultItem(item, cipher);
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            this.result.ciphers.push(cipher);
        });
        this.result.success = true;
        return Promise.resolve(this.result);
    }
    processWinOpVaultItem(item, cipher) {
        if (item.overview != null) {
            cipher.name = this.getValueOrDefault(item.overview.title);
            if (item.overview.URLs != null) {
                const urls = [];
                item.overview.URLs.forEach((url) => {
                    if (!this.isNullOrWhitespace(url.u)) {
                        urls.push(url.u);
                    }
                });
                cipher.login.uris = this.makeUriArray(urls);
            }
        }
        if (item.details != null) {
            if (item.details.passwordHistory != null) {
                this.parsePasswordHistory(item.details.passwordHistory, cipher);
            }
            if (!this.isNullOrWhitespace(item.details.ccnum) ||
                !this.isNullOrWhitespace(item.details.cvv)) {
                cipher.type = bw_CipherType.Card;
                cipher.card = new bw_CardView();
            }
            else if (!this.isNullOrWhitespace(item.details.firstname) ||
                !this.isNullOrWhitespace(item.details.address1)) {
                cipher.type = bw_CipherType.Identity;
                cipher.identity = new bw_IdentityView();
            }
            if (cipher.type === bw_CipherType.Login && !this.isNullOrWhitespace(item.details.password)) {
                cipher.login.password = item.details.password;
            }
            if (!this.isNullOrWhitespace(item.details.notesPlain)) {
                cipher.notes = item.details.notesPlain.split(this.newLineRegex).join("\n") + "\n";
            }
            if (item.details.fields != null) {
                this.parseFields(item.details.fields, cipher, "designation", "value", "name");
            }
            if (item.details.sections != null) {
                item.details.sections.forEach((section) => {
                    if (section.fields != null) {
                        this.parseFields(section.fields, cipher, "n", "v", "t");
                    }
                });
            }
        }
    }
    processStandardItem(item, cipher) {
        cipher.favorite = item.openContents && item.openContents.faveIndex ? true : false;
        cipher.name = this.getValueOrDefault(item.title);
        if (item.typeName === "securenotes.SecureNote") {
            cipher.type = bw_CipherType.SecureNote;
            cipher.secureNote = new bw_SecureNoteView();
            cipher.secureNote.type = bw_SecureNoteType.Generic;
        }
        else if (item.typeName === "wallet.financial.CreditCard") {
            cipher.type = bw_CipherType.Card;
            cipher.card = new bw_CardView();
        }
        else if (item.typeName === "identities.Identity") {
            cipher.type = bw_CipherType.Identity;
            cipher.identity = new bw_IdentityView();
        }
        else {
            cipher.login.uris = this.makeUriArray(item.location);
        }
        if (item.secureContents != null) {
            if (item.secureContents.passwordHistory != null) {
                this.parsePasswordHistory(item.secureContents.passwordHistory, cipher);
            }
            if (!this.isNullOrWhitespace(item.secureContents.notesPlain)) {
                cipher.notes = item.secureContents.notesPlain.split(this.newLineRegex).join("\n") + "\n";
            }
            if (cipher.type === bw_CipherType.Login) {
                if (!this.isNullOrWhitespace(item.secureContents.password)) {
                    cipher.login.password = item.secureContents.password;
                }
                if (item.secureContents.URLs != null) {
                    const urls = [];
                    item.secureContents.URLs.forEach((u) => {
                        if (!this.isNullOrWhitespace(u.url)) {
                            urls.push(u.url);
                        }
                    });
                    if (urls.length > 0) {
                        cipher.login.uris = this.makeUriArray(urls);
                    }
                }
            }
            if (item.secureContents.fields != null) {
                this.parseFields(item.secureContents.fields, cipher, "designation", "value", "name");
            }
            if (item.secureContents.sections != null) {
                item.secureContents.sections.forEach((section) => {
                    if (section.fields != null) {
                        this.parseFields(section.fields, cipher, "n", "v", "t");
                    }
                });
            }
        }
    }
    parsePasswordHistory(items, cipher) {
        const maxSize = items.length > 5 ? 5 : items.length;
        cipher.passwordHistory = items
            .filter((h) => !this.isNullOrWhitespace(h.value) && h.time != null)
            .sort((a, b) => b.time - a.time)
            .slice(0, maxSize)
            .map((h) => {
            const ph = new bw_PasswordHistoryView();
            ph.password = h.value;
            ph.lastUsedDate = new Date(("" + h.time).length >= 13 ? h.time : h.time * 1000);
            return ph;
        });
    }
    parseFields(fields, cipher, designationKey, valueKey, nameKey) {
        fields.forEach((field) => {
            if (field[valueKey] == null || field[valueKey].toString().trim() === "") {
                return;
            }
            // TODO: when date FieldType exists, store this as a date field type instead of formatted Text if k is 'date'
            const fieldValue = field.k === "date"
                ? new Date(field[valueKey] * 1000).toUTCString()
                : field[valueKey].toString();
            const fieldDesignation = field[designationKey] != null ? field[designationKey].toString() : null;
            if (cipher.type === bw_CipherType.Login) {
                if (this.isNullOrWhitespace(cipher.login.username) && fieldDesignation === "username") {
                    cipher.login.username = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(cipher.login.password) &&
                    fieldDesignation === "password") {
                    cipher.login.password = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(cipher.login.totp) &&
                    fieldDesignation != null &&
                    fieldDesignation.startsWith("TOTP_")) {
                    cipher.login.totp = fieldValue;
                    return;
                }
            }
            else if (cipher.type === bw_CipherType.Card) {
                if (this.isNullOrWhitespace(cipher.card.number) && fieldDesignation === "ccnum") {
                    cipher.card.number = fieldValue;
                    cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                    return;
                }
                else if (this.isNullOrWhitespace(cipher.card.code) && fieldDesignation === "cvv") {
                    cipher.card.code = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(cipher.card.cardholderName) &&
                    fieldDesignation === "cardholder") {
                    cipher.card.cardholderName = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(cipher.card.expiration) &&
                    fieldDesignation === "expiry" &&
                    fieldValue.length === 6) {
                    cipher.card.expMonth = fieldValue.substr(4, 2);
                    if (cipher.card.expMonth[0] === "0") {
                        cipher.card.expMonth = cipher.card.expMonth.substr(1, 1);
                    }
                    cipher.card.expYear = fieldValue.substr(0, 4);
                    return;
                }
                else if (fieldDesignation === "type") {
                    // Skip since brand was determined from number above
                    return;
                }
            }
            else if (cipher.type === bw_CipherType.Identity) {
                const identity = cipher.identity;
                if (this.isNullOrWhitespace(identity.firstName) && fieldDesignation === "firstname") {
                    identity.firstName = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(identity.lastName) && fieldDesignation === "lastname") {
                    identity.lastName = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(identity.middleName) && fieldDesignation === "initial") {
                    identity.middleName = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(identity.phone) && fieldDesignation === "defphone") {
                    identity.phone = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(identity.company) && fieldDesignation === "company") {
                    identity.company = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(identity.email) && fieldDesignation === "email") {
                    identity.email = fieldValue;
                    return;
                }
                else if (this.isNullOrWhitespace(identity.username) && fieldDesignation === "username") {
                    identity.username = fieldValue;
                    return;
                }
                else if (fieldDesignation === "address") {
                    // fieldValue is an object casted into a string, so access the plain value instead
                    const { street, city, country, zip } = field[valueKey];
                    identity.address1 = this.getValueOrDefault(street);
                    identity.city = this.getValueOrDefault(city);
                    if (!this.isNullOrWhitespace(country)) {
                        identity.country = country.toUpperCase();
                    }
                    identity.postalCode = this.getValueOrDefault(zip);
                    return;
                }
            }
            const fieldName = this.isNullOrWhitespace(field[nameKey]) ? "no_name" : field[nameKey];
            if (fieldName === "password" &&
                cipher.passwordHistory != null &&
                cipher.passwordHistory.some((h) => h.password === fieldValue)) {
                return;
            }
            const fieldType = field.k === "concealed" ? bw_FieldType.Hidden : bw_FieldType.Text;
            this.processKvp(cipher, fieldName, fieldValue, fieldType);
        });
    }
}

;// ../../libs/importer/src/importers/onepassword/types/onepassword-1pux-importer-types.ts
var bw_CategoryEnum;
(function (CategoryEnum) {
    CategoryEnum["Login"] = "001";
    CategoryEnum["CreditCard"] = "002";
    CategoryEnum["SecureNote"] = "003";
    CategoryEnum["Identity"] = "004";
    CategoryEnum["Password"] = "005";
    CategoryEnum["Document"] = "006";
    CategoryEnum["SoftwareLicense"] = "100";
    CategoryEnum["BankAccount"] = "101";
    CategoryEnum["Database"] = "102";
    CategoryEnum["DriversLicense"] = "103";
    CategoryEnum["OutdoorLicense"] = "104";
    CategoryEnum["Membership"] = "105";
    CategoryEnum["Passport"] = "106";
    CategoryEnum["RewardsProgram"] = "107";
    CategoryEnum["SocialSecurityNumber"] = "108";
    CategoryEnum["WirelessRouter"] = "109";
    CategoryEnum["Server"] = "110";
    CategoryEnum["EmailAccount"] = "111";
    CategoryEnum["API_Credential"] = "112";
    CategoryEnum["MedicalRecord"] = "113";
})(bw_CategoryEnum || (bw_CategoryEnum = {}));
var bw_LoginFieldTypeEnum;
(function (LoginFieldTypeEnum) {
    LoginFieldTypeEnum["TextOrHtml"] = "T";
    LoginFieldTypeEnum["EmailAddress"] = "E";
    LoginFieldTypeEnum["URL"] = "U";
    LoginFieldTypeEnum["Number"] = "N";
    LoginFieldTypeEnum["Password"] = "P";
    LoginFieldTypeEnum["TextArea"] = "A";
    LoginFieldTypeEnum["PhoneNumber"] = "TEL";
    LoginFieldTypeEnum["CheckBox"] = "C";
})(bw_LoginFieldTypeEnum || (bw_LoginFieldTypeEnum = {}));

;// ../../libs/importer/src/importers/onepassword/onepassword-1pux-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore










class bw_OnePassword1PuxImporter extends bw_base_importer_BaseImporter {
    constructor() {
        super(...arguments);
        this.result = new bw_import_result_ImportResult();
    }
    parse(data) {
        const exportData = JSON.parse(data);
        const account = exportData.accounts[0];
        // TODO Add handling of multiple vaults
        // const personalVaults = account.vaults[0].filter((v) => v.attrs.type === VaultAttributeTypeEnum.Personal);
        account.vaults.forEach((vault) => {
            vault.items.forEach((item) => {
                if (item.state === "archived") {
                    return;
                }
                const cipher = this.initLoginCipher();
                const category = item.categoryUuid;
                switch (category) {
                    case bw_CategoryEnum.Login:
                    case bw_CategoryEnum.Database:
                    case bw_CategoryEnum.Password:
                    case bw_CategoryEnum.WirelessRouter:
                    case bw_CategoryEnum.Server:
                    case bw_CategoryEnum.API_Credential:
                        cipher.type = bw_CipherType.Login;
                        cipher.login = new bw_LoginView();
                        break;
                    case bw_CategoryEnum.CreditCard:
                    case bw_CategoryEnum.BankAccount:
                        cipher.type = bw_CipherType.Card;
                        cipher.card = new bw_CardView();
                        break;
                    case bw_CategoryEnum.SecureNote:
                    case bw_CategoryEnum.SoftwareLicense:
                    case bw_CategoryEnum.EmailAccount:
                    case bw_CategoryEnum.MedicalRecord:
                        // case CategoryEnum.Document:
                        cipher.type = bw_CipherType.SecureNote;
                        cipher.secureNote = new bw_SecureNoteView();
                        cipher.secureNote.type = bw_SecureNoteType.Generic;
                        break;
                    case bw_CategoryEnum.Identity:
                    case bw_CategoryEnum.DriversLicense:
                    case bw_CategoryEnum.OutdoorLicense:
                    case bw_CategoryEnum.Membership:
                    case bw_CategoryEnum.Passport:
                    case bw_CategoryEnum.RewardsProgram:
                    case bw_CategoryEnum.SocialSecurityNumber:
                        cipher.type = bw_CipherType.Identity;
                        cipher.identity = new bw_IdentityView();
                        break;
                    default:
                        break;
                }
                cipher.favorite = item.favIndex === 1 ? true : false;
                this.processOverview(item.overview, cipher);
                this.processLoginFields(item, cipher);
                this.processDetails(category, item.details, cipher);
                this.parsePasswordHistory(item.details.passwordHistory, cipher);
                this.processSections(category, item.details.sections, cipher);
                if (!this.isNullOrWhitespace(item.details.notesPlain)) {
                    cipher.notes = item.details.notesPlain.split(this.newLineRegex).join("\n") + "\n";
                }
                this.convertToNoteIfNeeded(cipher);
                this.cleanupCipher(cipher);
                this.result.ciphers.push(cipher);
            });
        });
        if (this.organization) {
            this.moveFoldersToCollections(this.result);
        }
        this.result.success = true;
        return Promise.resolve(this.result);
    }
    processOverview(overview, cipher) {
        if (overview == null) {
            return;
        }
        cipher.name = this.getValueOrDefault(overview.title);
        if (overview.urls != null) {
            const urls = [];
            overview.urls.forEach((url) => {
                if (!this.isNullOrWhitespace(url.url)) {
                    urls.push(url.url);
                }
            });
            cipher.login.uris = this.makeUriArray(urls);
        }
        if (overview.tags != null && overview.tags.length > 0) {
            const folderName = this.capitalize(overview.tags[0]);
            this.processFolder(this.result, folderName);
        }
    }
    capitalize(inputString) {
        return inputString.trim().replace(/\w\S*/g, (w) => w.replace(/^\w/, (c) => c.toUpperCase()));
    }
    processLoginFields(item, cipher) {
        if (item.details == null) {
            return;
        }
        if (item.details.loginFields == null || item.details.loginFields.length === 0) {
            return;
        }
        item.details.loginFields.forEach((loginField) => {
            if (loginField.designation === "username" && loginField.value !== "") {
                cipher.type = bw_CipherType.Login;
                cipher.login.username = loginField.value;
                return;
            }
            if (loginField.designation === "password" && loginField.value !== "") {
                cipher.type = bw_CipherType.Login;
                cipher.login.password = loginField.value;
                return;
            }
            let fieldValue = loginField.value;
            let fieldType = bw_FieldType.Text;
            switch (loginField.fieldType) {
                case bw_LoginFieldTypeEnum.Password:
                    fieldType = bw_FieldType.Hidden;
                    break;
                case bw_LoginFieldTypeEnum.CheckBox:
                    fieldValue = loginField.value !== "" ? "true" : "false";
                    fieldType = bw_FieldType.Boolean;
                    break;
                default:
                    break;
            }
            this.processKvp(cipher, loginField.name, fieldValue, fieldType);
        });
    }
    processDetails(category, details, cipher) {
        if (category !== bw_CategoryEnum.Password) {
            return;
        }
        if (details == null) {
            return;
        }
        cipher.login.password = details.password;
    }
    processSections(category, sections, cipher) {
        if (sections == null || sections.length === 0) {
            return;
        }
        sections.forEach((section) => {
            if (section.fields == null) {
                return;
            }
            this.parseSectionFields(category, section.fields, cipher, section.title);
        });
    }
    parseSectionFields(category, fields, cipher, sectionTitle) {
        fields.forEach((field) => {
            const valueKey = Object.keys(field.value)[0];
            const anyField = field;
            if (anyField.value == null ||
                anyField.value[valueKey] == null ||
                anyField.value[valueKey] === "") {
                return;
            }
            const fieldName = this.getFieldName(field.title, sectionTitle);
            const fieldValue = this.extractValue(field.value, valueKey);
            if (cipher.type === bw_CipherType.Login) {
                if (this.fillLogin(field, fieldValue, cipher)) {
                    return;
                }
                switch (category) {
                    case bw_CategoryEnum.Login:
                    case bw_CategoryEnum.Database:
                    case bw_CategoryEnum.EmailAccount:
                    case bw_CategoryEnum.WirelessRouter:
                        break;
                    case bw_CategoryEnum.Server:
                        if (this.isNullOrWhitespace(cipher.login.uri) && field.id === "url") {
                            cipher.login.uris = this.makeUriArray(fieldValue);
                            return;
                        }
                        break;
                    case bw_CategoryEnum.API_Credential:
                        if (this.fillApiCredentials(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    default:
                        break;
                }
            }
            else if (cipher.type === bw_CipherType.Card) {
                if (this.fillCreditCard(field, fieldValue, cipher)) {
                    return;
                }
                if (category === bw_CategoryEnum.BankAccount) {
                    if (this.fillBankAccount(field, fieldValue, cipher)) {
                        return;
                    }
                }
            }
            else if (cipher.type === bw_CipherType.Identity) {
                if (this.fillIdentity(field, fieldValue, cipher, valueKey)) {
                    return;
                }
                if (valueKey === "address") {
                    // fieldValue is an object casted into a string, so access the plain value instead
                    const { street, city, country, zip, state } = field.value.address;
                    cipher.identity.address1 = this.getValueOrDefault(street);
                    cipher.identity.city = this.getValueOrDefault(city);
                    if (!this.isNullOrWhitespace(country)) {
                        cipher.identity.country = country.toUpperCase();
                    }
                    cipher.identity.postalCode = this.getValueOrDefault(zip);
                    cipher.identity.state = this.getValueOrDefault(state);
                    return;
                }
                switch (category) {
                    case bw_CategoryEnum.Identity:
                        break;
                    case bw_CategoryEnum.DriversLicense:
                        if (this.fillDriversLicense(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    case bw_CategoryEnum.OutdoorLicense:
                        if (this.fillOutdoorLicense(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    case bw_CategoryEnum.Membership:
                        if (this.fillMembership(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    case bw_CategoryEnum.Passport:
                        if (this.fillPassport(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    case bw_CategoryEnum.RewardsProgram:
                        if (this.fillRewardsProgram(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    case bw_CategoryEnum.SocialSecurityNumber:
                        if (this.fillSSN(field, fieldValue, cipher)) {
                            return;
                        }
                        break;
                    default:
                        break;
                }
            }
            if (valueKey === "email") {
                // fieldValue is an object casted into a string, so access the plain value instead
                const { email_address, provider } = field.value.email;
                this.processKvp(cipher, fieldName, email_address, bw_FieldType.Text);
                this.processKvp(cipher, "provider", provider, bw_FieldType.Text);
                return;
            }
            // Do not include a password field if it's already in the history
            if (field.title === "password" &&
                cipher.passwordHistory != null &&
                cipher.passwordHistory.some((h) => h.password === fieldValue)) {
                return;
            }
            // TODO ?? If one of the fields is marked as guarded, then activate Password-Reprompt for the entire item
            if (field.guarded && cipher.reprompt === bw_CipherRepromptType.None) {
                cipher.reprompt = bw_CipherRepromptType.Password;
            }
            const fieldType = valueKey === "concealed" ? bw_FieldType.Hidden : bw_FieldType.Text;
            this.processKvp(cipher, fieldName, fieldValue, fieldType);
        });
    }
    // Use the title if available. If not use the sectionTitle if available.
    // Default to an empty string in all other cases.
    getFieldName(title, sectionTitle) {
        if (!this.isNullOrWhitespace(title)) {
            return title;
        }
        if (!this.isNullOrWhitespace(sectionTitle)) {
            return sectionTitle;
        }
        return "";
    }
    extractValue(value, valueKey) {
        if (valueKey === "date") {
            return new Date(value.date * 1000).toUTCString();
        }
        if (valueKey === "monthYear") {
            return value.monthYear.toString();
        }
        return value[valueKey];
    }
    fillLogin(field, fieldValue, cipher) {
        const fieldName = this.getFieldName(field.title);
        if (this.isNullOrWhitespace(cipher.login.username) && fieldName === "username") {
            cipher.login.username = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.login.password) && fieldName === "password") {
            cipher.login.password = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.login.totp) &&
            field.id != null &&
            field.id.startsWith("TOTP_")) {
            cipher.login.totp = fieldValue;
            return true;
        }
        return false;
    }
    fillApiCredentials(field, fieldValue, cipher) {
        const fieldName = this.getFieldName(field.title);
        if (this.isNullOrWhitespace(cipher.login.password) && fieldName === "credential") {
            cipher.login.password = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.login.uri) && fieldName === "hostname") {
            cipher.login.uris = this.makeUriArray(fieldValue);
            return true;
        }
        return false;
    }
    fillCreditCard(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.card.number) && field.id === "ccnum") {
            cipher.card.number = fieldValue;
            cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
            return true;
        }
        if (this.isNullOrWhitespace(cipher.card.code) && field.id === "cvv") {
            cipher.card.code = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.card.cardholderName) && field.id === "cardholder") {
            cipher.card.cardholderName = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.card.expiration) && field.id === "expiry") {
            const monthYear = fieldValue.toString().trim();
            cipher.card.expMonth = monthYear.substring(4, 6);
            if (cipher.card.expMonth[0] === "0") {
                cipher.card.expMonth = cipher.card.expMonth.substring(1, 2);
            }
            cipher.card.expYear = monthYear.substring(0, 4);
            return true;
        }
        if (field.id === "type") {
            // Skip since brand was determined from number above
            return true;
        }
        return false;
    }
    fillBankAccount(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.card.cardholderName) && field.id === "owner") {
            cipher.card.cardholderName = fieldValue;
            return true;
        }
        return false;
    }
    fillIdentity(field, fieldValue, cipher, valueKey) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "firstname") {
            cipher.identity.firstName = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.lastName) && field.id === "lastname") {
            cipher.identity.lastName = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.middleName) && field.id === "initial") {
            cipher.identity.middleName = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.phone) && field.id === "defphone") {
            cipher.identity.phone = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.company) && field.id === "company") {
            cipher.identity.company = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.email)) {
            if (valueKey === "email") {
                const { email_address, provider } = field.value.email;
                cipher.identity.email = this.getValueOrDefault(email_address);
                this.processKvp(cipher, "provider", provider, bw_FieldType.Text);
                return true;
            }
            if (field.id === "email") {
                cipher.identity.email = fieldValue;
                return true;
            }
        }
        if (this.isNullOrWhitespace(cipher.identity.username) && field.id === "username") {
            cipher.identity.username = fieldValue;
            return true;
        }
        return false;
    }
    fillDriversLicense(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "fullname") {
            this.processFullName(cipher, fieldValue);
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.address1) && field.id === "address") {
            cipher.identity.address1 = fieldValue;
            return true;
        }
        // TODO ISO code
        if (this.isNullOrWhitespace(cipher.identity.country) && field.id === "country") {
            cipher.identity.country = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.state) && field.id === "state") {
            cipher.identity.state = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.licenseNumber) && field.id === "number") {
            cipher.identity.licenseNumber = fieldValue;
            return true;
        }
        return false;
    }
    fillOutdoorLicense(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "name") {
            this.processFullName(cipher, fieldValue);
            return true;
        }
        // TODO ISO code
        if (this.isNullOrWhitespace(cipher.identity.country) && field.id === "country") {
            cipher.identity.country = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.state) && field.id === "state") {
            cipher.identity.state = fieldValue;
            return true;
        }
        return false;
    }
    fillMembership(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "member_name") {
            this.processFullName(cipher, fieldValue);
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.company) && field.id === "org_name") {
            cipher.identity.company = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.phone) && field.id === "phone") {
            cipher.identity.phone = fieldValue;
            return true;
        }
        return false;
    }
    fillPassport(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "fullname") {
            this.processFullName(cipher, fieldValue);
            return true;
        }
        // TODO Iso
        if (this.isNullOrWhitespace(cipher.identity.country) && field.id === "issuing_country") {
            cipher.identity.country = fieldValue;
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.passportNumber) && field.id === "number") {
            cipher.identity.passportNumber = fieldValue;
            return true;
        }
        return false;
    }
    fillRewardsProgram(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "member_name") {
            this.processFullName(cipher, fieldValue);
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.company) && field.id === "company_name") {
            cipher.identity.company = fieldValue;
            return true;
        }
        return false;
    }
    fillSSN(field, fieldValue, cipher) {
        if (this.isNullOrWhitespace(cipher.identity.firstName) && field.id === "name") {
            this.processFullName(cipher, fieldValue);
            return true;
        }
        if (this.isNullOrWhitespace(cipher.identity.ssn) && field.id === "number") {
            cipher.identity.ssn = fieldValue;
            return true;
        }
        return false;
    }
    parsePasswordHistory(historyItems, cipher) {
        if (historyItems == null || historyItems.length === 0) {
            return;
        }
        const maxSize = historyItems.length > 5 ? 5 : historyItems.length;
        cipher.passwordHistory = historyItems
            .filter((h) => !this.isNullOrWhitespace(h.value) && h.time != null)
            .sort((a, b) => b.time - a.time)
            .slice(0, maxSize)
            .map((h) => {
            const ph = new bw_PasswordHistoryView();
            ph.password = h.value;
            ph.lastUsedDate = new Date(("" + h.time).length >= 13 ? h.time : h.time * 1000);
            return ph;
        });
    }
}

;// ../../libs/importer/src/importers/onepassword/cipher-import-context.ts
class bw_CipherImportContext {
    constructor(importRecord, property, cipher) {
        this.importRecord = importRecord;
        this.property = property;
        this.cipher = cipher;
        this.lowerProperty = property.toLowerCase();
    }
}

;// ../../libs/importer/src/importers/onepassword/onepassword-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





const bw_IgnoredProperties = [
    "ainfo",
    "autosubmit",
    "notesplain",
    "ps",
    "scope",
    "tags",
    "title",
    "uuid",
    "notes",
];
class bw_OnePasswordCsvImporter extends bw_base_importer_BaseImporter {
    constructor() {
        super(...arguments);
        this.loginPropertyParsers = [
            this.setLoginUsername,
            this.setLoginPassword,
            this.setLoginUris,
        ];
        this.creditCardPropertyParsers = [
            this.setCreditCardNumber,
            this.setCreditCardVerification,
            this.setCreditCardCardholderName,
            this.setCreditCardExpiry,
        ];
        this.identityPropertyParsers = [
            this.setIdentityFirstName,
            this.setIdentityInitial,
            this.setIdentityLastName,
            this.setIdentityUserName,
            this.setIdentityEmail,
            this.setIdentityPhone,
            this.setIdentityCompany,
        ];
    }
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true, {
            quoteChar: '"',
            escapeChar: "\\",
        });
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (this.isNullOrWhitespace(this.getProp(value, "title"))) {
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(this.getProp(value, "title"), "--");
            this.setNotes(value, cipher);
            this.setCipherType(value, cipher);
            let altUsername = null;
            for (const property in value) {
                // eslint-disable-next-line
                if (!value.hasOwnProperty(property) || this.isNullOrWhitespace(value[property])) {
                    continue;
                }
                const context = new bw_CipherImportContext(value, property, cipher);
                if (cipher.type === bw_CipherType.Login && this.setKnownLoginValue(context)) {
                    continue;
                }
                else if (cipher.type === bw_CipherType.Card && this.setKnownCreditCardValue(context)) {
                    continue;
                }
                else if (cipher.type === bw_CipherType.Identity && this.setKnownIdentityValue(context)) {
                    continue;
                }
                altUsername = this.setUnknownValue(context, altUsername);
            }
            if (cipher.type === bw_CipherType.Login &&
                !this.isNullOrWhitespace(altUsername) &&
                this.isNullOrWhitespace(cipher.login.username) &&
                altUsername.indexOf("://") === -1) {
                cipher.login.username = altUsername;
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
    getProp(obj, name) {
        const lowerObj = Object.entries(obj).reduce((agg, entry) => {
            agg[entry[0].toLowerCase()] = entry[1];
            return agg;
        }, {});
        return lowerObj[name.toLowerCase()];
    }
    getPropByRegexp(obj, regexp) {
        const matchingKeys = Object.keys(obj).reduce((agg, key) => {
            if (key.match(regexp)) {
                agg.push(key);
            }
            return agg;
        }, []);
        if (matchingKeys.length === 0) {
            return null;
        }
        else {
            return obj[matchingKeys[0]];
        }
    }
    getPropIncluding(obj, name) {
        const includesMap = Object.keys(obj).reduce((agg, entry) => {
            if (entry.toLowerCase().includes(name.toLowerCase())) {
                agg.push(entry);
            }
            return agg;
        }, []);
        if (includesMap.length === 0) {
            return null;
        }
        else {
            return obj[includesMap[0]];
        }
    }
    setNotes(importRecord, cipher) {
        cipher.notes =
            this.getValueOrDefault(this.getProp(importRecord, "notesPlain"), "") +
                "\n" +
                this.getValueOrDefault(this.getProp(importRecord, "notes"), "") +
                "\n";
        cipher.notes.trim();
    }
    setKnownLoginValue(context) {
        return this.loginPropertyParsers.reduce((agg, func) => {
            if (!agg) {
                agg = func.bind(this)(context);
            }
            return agg;
        }, false);
    }
    setKnownCreditCardValue(context) {
        return this.creditCardPropertyParsers.reduce((agg, func) => {
            if (!agg) {
                agg = func.bind(this)(context);
            }
            return agg;
        }, false);
    }
    setKnownIdentityValue(context) {
        return this.identityPropertyParsers.reduce((agg, func) => {
            if (!agg) {
                agg = func.bind(this)(context);
            }
            return agg;
        }, false);
    }
    setUnknownValue(context, altUsername) {
        if (bw_IgnoredProperties.indexOf(context.lowerProperty) === -1 &&
            !context.lowerProperty.startsWith("section:") &&
            !context.lowerProperty.startsWith("section ")) {
            if (altUsername == null && context.lowerProperty === "email") {
                return context.importRecord[context.property];
            }
            else if (context.lowerProperty === "created date" ||
                context.lowerProperty === "modified date") {
                const readableDate = new Date(parseInt(context.importRecord[context.property], 10) * 1000).toUTCString();
                this.processKvp(context.cipher, "1Password " + context.property, readableDate);
                return null;
            }
            if (context.lowerProperty.includes("password") ||
                context.lowerProperty.includes("key") ||
                context.lowerProperty.includes("secret")) {
                this.processKvp(context.cipher, context.property, context.importRecord[context.property], bw_FieldType.Hidden);
            }
            else {
                this.processKvp(context.cipher, context.property, context.importRecord[context.property]);
            }
        }
        return null;
    }
    setIdentityFirstName(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.firstName) &&
            context.lowerProperty.includes("first name")) {
            context.cipher.identity.firstName = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setIdentityInitial(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.middleName) &&
            context.lowerProperty.includes("initial")) {
            context.cipher.identity.middleName = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setIdentityLastName(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.lastName) &&
            context.lowerProperty.includes("last name")) {
            context.cipher.identity.lastName = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setIdentityUserName(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.username) &&
            context.lowerProperty.includes("username")) {
            context.cipher.identity.username = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setIdentityCompany(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.company) &&
            context.lowerProperty.includes("company")) {
            context.cipher.identity.company = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setIdentityPhone(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.phone) &&
            context.lowerProperty.includes("default phone")) {
            context.cipher.identity.phone = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setIdentityEmail(context) {
        if (this.isNullOrWhitespace(context.cipher.identity.email) &&
            context.lowerProperty.includes("email")) {
            context.cipher.identity.email = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setCreditCardNumber(context) {
        if (this.isNullOrWhitespace(context.cipher.card.number) &&
            context.lowerProperty.includes("number")) {
            context.cipher.card.number = context.importRecord[context.property];
            context.cipher.card.brand = bw_CardView.getCardBrandByPatterns(context.cipher.card.number);
            return true;
        }
        return false;
    }
    setCreditCardVerification(context) {
        if (this.isNullOrWhitespace(context.cipher.card.code) &&
            context.lowerProperty.includes("verification number")) {
            context.cipher.card.code = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setCreditCardCardholderName(context) {
        if (this.isNullOrWhitespace(context.cipher.card.cardholderName) &&
            context.lowerProperty.includes("cardholder name")) {
            context.cipher.card.cardholderName = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setCreditCardExpiry(context) {
        if (this.isNullOrWhitespace(context.cipher.card.expiration) &&
            context.lowerProperty.includes("expiry date") &&
            context.importRecord[context.property].length === 7) {
            context.cipher.card.expMonth = context.importRecord[context.property].substr(0, 2);
            if (context.cipher.card.expMonth[0] === "0") {
                context.cipher.card.expMonth = context.cipher.card.expMonth.substr(1, 1);
            }
            context.cipher.card.expYear = context.importRecord[context.property].substr(3, 4);
            return true;
        }
        return false;
    }
    setLoginPassword(context) {
        if (this.isNullOrWhitespace(context.cipher.login.password) &&
            context.lowerProperty === "password") {
            context.cipher.login.password = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setLoginUsername(context) {
        if (this.isNullOrWhitespace(context.cipher.login.username) &&
            context.lowerProperty === "username") {
            context.cipher.login.username = context.importRecord[context.property];
            return true;
        }
        return false;
    }
    setLoginUris(context) {
        if ((context.cipher.login.uris == null || context.cipher.login.uris.length === 0) &&
            context.lowerProperty === "urls") {
            const urls = context.importRecord[context.property].split(this.newLineRegex);
            context.cipher.login.uris = this.makeUriArray(urls);
            return true;
        }
        else if (context.lowerProperty === "url") {
            if (context.cipher.login.uris == null) {
                context.cipher.login.uris = [];
            }
            context.cipher.login.uris.concat(this.makeUriArray(context.importRecord[context.property]));
            return true;
        }
        return false;
    }
}

;// ../../libs/importer/src/importers/onepassword/onepassword-mac-csv-importer.ts




class bw_OnePasswordMacCsvImporter extends bw_OnePasswordCsvImporter {
    setCipherType(value, cipher) {
        const onePassType = this.getValueOrDefault(this.getProp(value, "type"), "Login");
        switch (onePassType) {
            case "Credit Card":
                cipher.type = bw_CipherType.Card;
                cipher.card = new bw_CardView();
                bw_IgnoredProperties.push("type");
                break;
            case "Identity":
                cipher.type = bw_CipherType.Identity;
                cipher.identity = new bw_IdentityView();
                bw_IgnoredProperties.push("type");
                break;
            case "Login":
            case "Secure Note":
                bw_IgnoredProperties.push("type");
                break;
            default:
                break;
        }
    }
}

;// ../../libs/importer/src/importers/onepassword/onepassword-win-csv-importer.ts





class bw_OnePasswordWinCsvImporter extends bw_OnePasswordCsvImporter {
    constructor() {
        super();
        this.identityPropertyParsers.push(this.setIdentityAddress);
    }
    setCipherType(value, cipher) {
        cipher.type = bw_CipherType.Login;
        cipher.login = new bw_LoginView();
        if (!this.isNullOrWhitespace(this.getPropByRegexp(value, /\d+: number/i)) &&
            !this.isNullOrWhitespace(this.getPropByRegexp(value, /\d+: expiry date/i))) {
            cipher.type = bw_CipherType.Card;
            cipher.card = new bw_CardView();
        }
        if (!this.isNullOrWhitespace(this.getPropByRegexp(value, /name \d+: first name/i)) ||
            !this.isNullOrWhitespace(this.getPropByRegexp(value, /name \d+: initial/i)) ||
            !this.isNullOrWhitespace(this.getPropByRegexp(value, /name \d+: last name/i)) ||
            !this.isNullOrWhitespace(this.getPropByRegexp(value, /internet \d+: email/i))) {
            cipher.type = bw_CipherType.Identity;
            cipher.identity = new bw_IdentityView();
        }
    }
    setIdentityAddress(context) {
        if (context.lowerProperty.match(/address \d+: address/i)) {
            this.processKvp(context.cipher, "address", context.importRecord[context.property]);
            return true;
        }
        return false;
    }
    setCreditCardExpiry(context) {
        if (this.isNullOrWhitespace(context.cipher.card.expiration) &&
            context.lowerProperty.includes("expiry date")) {
            const expSplit = context.importRecord[context.property].split("/");
            context.cipher.card.expMonth = expSplit[0];
            if (context.cipher.card.expMonth[0] === "0" && context.cipher.card.expMonth.length === 2) {
                context.cipher.card.expMonth = context.cipher.card.expMonth.substr(1, 1);
            }
            context.cipher.card.expYear = expSplit[2].length > 4 ? expSplit[2].substr(0, 4) : expSplit[2];
            return true;
        }
        return false;
    }
}

;// ../../libs/importer/src/importers/onepassword/index.ts






;// ../../libs/importer/src/importers/padlock-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_PadlockCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        let headers = null;
        results.forEach((value) => {
            if (headers == null) {
                headers = value.map((v) => v);
                return;
            }
            if (value.length < 2 || value.length !== headers.length) {
                return;
            }
            if (!this.isNullOrWhitespace(value[1])) {
                if (this.organization) {
                    const tags = value[1].split(",");
                    tags.forEach((tag) => {
                        tag = tag.trim();
                        let addCollection = true;
                        let collectionIndex = result.collections.length;
                        for (let i = 0; i < result.collections.length; i++) {
                            if (result.collections[i].name === tag) {
                                addCollection = false;
                                collectionIndex = i;
                                break;
                            }
                        }
                        if (addCollection) {
                            const collection = new bw_CollectionView();
                            collection.name = tag;
                            result.collections.push(collection);
                        }
                        result.collectionRelationships.push([result.ciphers.length, collectionIndex]);
                    });
                }
                else {
                    const tags = value[1].split(",");
                    const tag = tags.length > 0 ? tags[0].trim() : null;
                    this.processFolder(result, tag);
                }
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value[0], "--");
            for (let i = 2; i < value.length; i++) {
                const header = headers[i].trim().toLowerCase();
                if (this.isNullOrWhitespace(value[i]) || this.isNullOrWhitespace(header)) {
                    continue;
                }
                if (this.usernameFieldNames.indexOf(header) > -1) {
                    cipher.login.username = value[i];
                }
                else if (this.passwordFieldNames.indexOf(header) > -1) {
                    cipher.login.password = value[i];
                }
                else if (this.uriFieldNames.indexOf(header) > -1) {
                    cipher.login.uris = this.makeUriArray(value[i]);
                }
                else {
                    this.processKvp(cipher, headers[i], value[i]);
                }
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passkeep-csv-importer.ts


class bw_PassKeepCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            this.processFolder(result, this.getValue("category", value));
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValue("description", value);
            cipher.name = this.getValueOrDefault(this.getValue("title", value), "--");
            cipher.login.username = this.getValue("username", value);
            cipher.login.password = this.getValue("password", value);
            cipher.login.uris = this.makeUriArray(this.getValue("site", value));
            this.processKvp(cipher, "Password 2", this.getValue("password2", value));
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    getValue(key, value) {
        return this.getValueOrDefault(value[key], this.getValueOrDefault(value[" " + key]));
    }
}

;// ../../libs/importer/src/importers/passky/passky-json-importer.ts


class bw_PasskyJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const passkyExport = JSON.parse(data);
        if (passkyExport == null ||
            passkyExport.passwords == null ||
            passkyExport.passwords.length === 0) {
            result.success = false;
            return Promise.resolve(result);
        }
        if (passkyExport.encrypted == true) {
            result.success = false;
            result.errorMessage = "Unable to import an encrypted passky backup.";
            return Promise.resolve(result);
        }
        passkyExport.passwords.forEach((record) => {
            const cipher = this.initLoginCipher();
            cipher.name = record.website;
            cipher.login.username = record.username;
            cipher.login.password = record.password;
            cipher.login.uris = this.makeUriArray(record.website);
            cipher.notes = record.message;
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passman-json-importer.ts


class bw_PassmanJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || results.length === 0) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((credential) => {
            if (credential.tags != null && credential.tags.length > 0) {
                const folderName = credential.tags[0].text;
                this.processFolder(result, folderName);
            }
            const cipher = this.initLoginCipher();
            cipher.name = credential.label;
            cipher.login.username = this.getValueOrDefault(credential.username);
            if (this.isNullOrWhitespace(cipher.login.username)) {
                cipher.login.username = this.getValueOrDefault(credential.email);
            }
            else if (!this.isNullOrWhitespace(credential.email)) {
                cipher.notes = "Email: " + credential.email + "\n";
            }
            cipher.login.password = this.getValueOrDefault(credential.password);
            cipher.login.uris = this.makeUriArray(credential.url);
            cipher.notes += this.getValueOrDefault(credential.description, "");
            if (credential.otp != null) {
                cipher.login.totp = this.getValueOrDefault(credential.otp.secret);
            }
            if (credential.custom_fields != null) {
                credential.custom_fields.forEach((customField) => {
                    switch (customField.field_type) {
                        case "text":
                        case "password":
                            this.processKvp(cipher, customField.label, customField.value);
                            break;
                    }
                });
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passpack-csv-importer.ts



class bw_PasspackCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const tagsJson = !this.isNullOrWhitespace(value.Tags) ? JSON.parse(value.Tags) : null;
            const tags = tagsJson != null && tagsJson.tags != null && tagsJson.tags.length > 0
                ? tagsJson.tags
                    .map((tagJson) => {
                    try {
                        const t = JSON.parse(tagJson);
                        return this.getValueOrDefault(t.tag);
                    }
                    catch (_a) {
                        // Ignore error
                    }
                    return null;
                })
                    .filter((t) => !this.isNullOrWhitespace(t))
                : null;
            if (this.organization && tags != null && tags.length > 0) {
                tags.forEach((tag) => {
                    let addCollection = true;
                    let collectionIndex = result.collections.length;
                    for (let i = 0; i < result.collections.length; i++) {
                        if (result.collections[i].name === tag) {
                            addCollection = false;
                            collectionIndex = i;
                            break;
                        }
                    }
                    if (addCollection) {
                        const collection = new bw_CollectionView();
                        collection.name = tag;
                        result.collections.push(collection);
                    }
                    result.collectionRelationships.push([result.ciphers.length, collectionIndex]);
                });
            }
            else if (!this.organization && tags != null && tags.length > 0) {
                this.processFolder(result, tags[0]);
            }
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValueOrDefault(value.Notes, "");
            cipher.notes += "\n\n" + this.getValueOrDefault(value["Shared Notes"], "") + "\n";
            cipher.name = this.getValueOrDefault(value["Entry Name"], "--");
            cipher.login.username = this.getValueOrDefault(value["User ID"]);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.uris = this.makeUriArray(value.URL);
            if (value.__parsed_extra != null && value.__parsed_extra.length > 0) {
                value.__parsed_extra.forEach((extra) => {
                    if (!this.isNullOrWhitespace(extra)) {
                        cipher.notes += "\n" + extra;
                    }
                });
            }
            const fieldsJson = !this.isNullOrWhitespace(value["Extra Fields"])
                ? JSON.parse(value["Extra Fields"])
                : null;
            const fields = fieldsJson != null && fieldsJson.extraFields != null && fieldsJson.extraFields.length > 0
                ? fieldsJson.extraFields.map((fieldJson) => {
                    try {
                        return JSON.parse(fieldJson);
                    }
                    catch (_a) {
                        // Ignore error
                    }
                    return null;
                })
                : null;
            if (fields != null) {
                fields.forEach((f) => {
                    if (f != null) {
                        this.processKvp(cipher, f.name, f.data);
                    }
                });
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passwordagent-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_PasswordAgentCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        let newVersion = true;
        results.forEach((value) => {
            if (value.length !== 5 && value.length < 9) {
                return;
            }
            const altFormat = value.length === 10 && value[0] === "0";
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value[altFormat ? 1 : 0], "--");
            cipher.login.username = this.getValueOrDefault(value[altFormat ? 2 : 1]);
            cipher.login.password = this.getValueOrDefault(value[altFormat ? 3 : 2]);
            if (value.length === 5) {
                newVersion = false;
                cipher.notes = this.getValueOrDefault(value[4]);
                cipher.login.uris = this.makeUriArray(value[3]);
            }
            else {
                const folder = this.getValueOrDefault(value[altFormat ? 9 : 8], "(None)");
                let folderName = folder !== "(None)" ? folder.split("\\").join("/") : null;
                if (folderName != null) {
                    folderName = folder.split(" > ").join("/");
                    folderName = folder.split(">").join("/");
                }
                this.processFolder(result, folderName);
                cipher.notes = this.getValueOrDefault(value[altFormat ? 5 : 3]);
                cipher.login.uris = this.makeUriArray(value[4]);
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (newVersion && this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passwordboss-json-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_PasswordBossJsonImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || results.items == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        const foldersMap = new Map();
        results.folders.forEach((value) => {
            foldersMap.set(value.id, value.name);
        });
        const foldersIndexMap = new Map();
        foldersMap.forEach((val, key) => {
            foldersIndexMap.set(key, result.folders.length);
            const f = new bw_FolderView();
            f.name = val;
            result.folders.push(f);
        });
        results.items.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.name, "--");
            cipher.login.uris = this.makeUriArray(value.login_url);
            if (value.folder != null && foldersIndexMap.has(value.folder)) {
                result.folderRelationships.push([result.ciphers.length, foldersIndexMap.get(value.folder)]);
            }
            if (value.identifiers == null) {
                return;
            }
            if (!this.isNullOrWhitespace(value.identifiers.notes)) {
                cipher.notes = value.identifiers.notes.split("\\r\\n").join("\n").split("\\n").join("\n");
            }
            if (value.type === "CreditCard") {
                cipher.card = new bw_CardView();
                cipher.type = bw_CipherType.Card;
            }
            for (const property in value.identifiers) {
                // eslint-disable-next-line
                if (!value.identifiers.hasOwnProperty(property)) {
                    continue;
                }
                const valObj = value.identifiers[property];
                const val = valObj != null ? valObj.toString() : null;
                if (this.isNullOrWhitespace(val) ||
                    property === "notes" ||
                    property === "ignoreItemInSecurityScore") {
                    continue;
                }
                if (property === "custom_fields") {
                    valObj.forEach((cf) => {
                        this.processKvp(cipher, cf.name, cf.value);
                    });
                    continue;
                }
                if (cipher.type === bw_CipherType.Card) {
                    if (property === "cardNumber") {
                        cipher.card.number = val;
                        cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                        continue;
                    }
                    else if (property === "nameOnCard") {
                        cipher.card.cardholderName = val;
                        continue;
                    }
                    else if (property === "security_code") {
                        cipher.card.code = val;
                        continue;
                    }
                    else if (property === "expires") {
                        try {
                            const expDate = new Date(val);
                            cipher.card.expYear = expDate.getFullYear().toString();
                            cipher.card.expMonth = (expDate.getMonth() + 1).toString();
                        }
                        catch (_a) {
                            // Ignore error
                        }
                        continue;
                    }
                    else if (property === "cardType") {
                        continue;
                    }
                }
                else {
                    if ((property === "username" || property === "email") &&
                        this.isNullOrWhitespace(cipher.login.username)) {
                        cipher.login.username = val;
                        continue;
                    }
                    else if (property === "password") {
                        cipher.login.password = val;
                        continue;
                    }
                    else if (property === "totp") {
                        cipher.login.totp = val;
                        continue;
                    }
                    else if ((cipher.login.uris == null || cipher.login.uris.length === 0) &&
                        this.uriFieldNames.indexOf(property) > -1) {
                        cipher.login.uris = this.makeUriArray(val);
                        continue;
                    }
                }
                this.processKvp(cipher, property, val);
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passworddragon-xml-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_PasswordDragonXmlImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const doc = this.parseXml(data);
        if (doc == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        const records = doc.querySelectorAll("PasswordManager > record");
        Array.from(records).forEach((record) => {
            const category = this.querySelectorDirectChild(record, "Category");
            const categoryText = category != null &&
                !this.isNullOrWhitespace(category.textContent) &&
                category.textContent !== "Unfiled"
                ? category.textContent
                : null;
            this.processFolder(result, categoryText);
            const accountName = this.querySelectorDirectChild(record, "Account-Name");
            const userId = this.querySelectorDirectChild(record, "User-Id");
            const password = this.querySelectorDirectChild(record, "Password");
            const url = this.querySelectorDirectChild(record, "URL");
            const notes = this.querySelectorDirectChild(record, "Notes");
            const cipher = this.initLoginCipher();
            cipher.name =
                accountName != null ? this.getValueOrDefault(accountName.textContent, "--") : "--";
            cipher.notes = notes != null ? this.getValueOrDefault(notes.textContent) : "";
            cipher.login.username = userId != null ? this.getValueOrDefault(userId.textContent) : null;
            cipher.login.password =
                password != null ? this.getValueOrDefault(password.textContent) : null;
            cipher.login.uris = url != null ? this.makeUriArray(url.textContent) : null;
            const attributes = [];
            for (let i = 1; i <= 10; i++) {
                attributes.push("Attribute-" + i);
            }
            this.querySelectorAllDirectChild(record, attributes.join(",")).forEach((attr) => {
                if (this.isNullOrWhitespace(attr.textContent) || attr.textContent === "null") {
                    return;
                }
                this.processKvp(cipher, attr.tagName, attr.textContent);
            });
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passwordsafe-xml-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/** This is the importer for the xml format from pwsafe.org  */
class bw_PasswordSafeXmlImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const doc = this.parseXml(data);
        if (doc == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        const passwordSafe = doc.querySelector("passwordsafe");
        if (passwordSafe == null) {
            result.errorMessage = "Missing `passwordsafe` node.";
            result.success = false;
            return Promise.resolve(result);
        }
        const notesDelimiter = passwordSafe.getAttribute("delimiter");
        const entries = doc.querySelectorAll("passwordsafe > entry");
        Array.from(entries).forEach((entry) => {
            const group = this.querySelectorDirectChild(entry, "group");
            const groupText = group != null && !this.isNullOrWhitespace(group.textContent)
                ? group.textContent.split(".").join("/")
                : null;
            this.processFolder(result, groupText);
            const title = this.querySelectorDirectChild(entry, "title");
            const username = this.querySelectorDirectChild(entry, "username");
            const email = this.querySelectorDirectChild(entry, "email");
            const password = this.querySelectorDirectChild(entry, "password");
            const url = this.querySelectorDirectChild(entry, "url");
            const notes = this.querySelectorDirectChild(entry, "notes");
            const cipher = this.initLoginCipher();
            cipher.name = title != null ? this.getValueOrDefault(title.textContent, "--") : "--";
            cipher.notes =
                notes != null
                    ? this.getValueOrDefault(notes.textContent, "").split(notesDelimiter).join("\n")
                    : null;
            cipher.login.username =
                username != null ? this.getValueOrDefault(username.textContent) : null;
            cipher.login.password =
                password != null ? this.getValueOrDefault(password.textContent) : null;
            cipher.login.uris = url != null ? this.makeUriArray(url.textContent) : null;
            if (this.isNullOrWhitespace(cipher.login.username) && email != null) {
                cipher.login.username = this.getValueOrDefault(email.textContent);
            }
            else if (email != null && !this.isNullOrWhitespace(email.textContent)) {
                cipher.notes = this.isNullOrWhitespace(cipher.notes)
                    ? "Email: " + email.textContent
                    : cipher.notes + "\n" + "Email: " + email.textContent;
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passwordwallet-txt-importer.ts


class bw_PasswordWalletTxtImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length < 1) {
                return;
            }
            if (value.length > 5) {
                this.processFolder(result, value[5]);
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value[0], "--");
            if (value.length > 4) {
                cipher.notes = this.getValueOrDefault(value[4], "").split("¬").join("\n");
            }
            if (value.length > 2) {
                cipher.login.username = this.getValueOrDefault(value[2]);
            }
            if (value.length > 3) {
                cipher.login.password = this.getValueOrDefault(value[3]);
            }
            if (value.length > 1) {
                cipher.login.uris = this.makeUriArray(value[1]);
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/passsordxp/dutch-csv-headers.ts
const bw_dutchHeaderTranslations = {
    Titel: "Title",
    Gebruikersnaam: "Username",
    Wachtwoord: "Password",
    Gewijzigd: "Modified",
    Gemaakt: "Created",
    "Verloopt op": "Expire on",
    Beschrijving: "Description",
    "Gewijzigd door": "Modified by",
};

;// ../../libs/importer/src/importers/passsordxp/german-csv-headers.ts
const bw_germanHeaderTranslations = {
    Titel: "Title",
    Benutzername: "Username",
    Konto: "Account",
    Passwort: "Password",
    "Geändert am": "Modified",
    "Erstellt am": "Created",
    "Läuft ab am": "Expire on",
    Beschreibung: "Description",
    "Geändert von": "Modified by",
};

;// ../../libs/importer/src/importers/passsordxp/passwordxp-csv-importer.ts



const bw_passwordxp_csv_importer_mappedColumns = new Set(["Title", "Username", "URL", "Password", "Description"]);


/* Translates the headers from non-English to English
 * This is necessary because the parser only maps English headers to ciphers
 * Currently only supports German and Dutch translations
 */
function bw_translateIntoEnglishHeaders(header) {
    const translations = Object.assign(Object.assign({ 
        // The header column 'User name' is parsed by the parser, but cannot be used as a variable. This converts it to a valid variable name, prior to parsing.
        "User name": "Username" }, bw_germanHeaderTranslations), bw_dutchHeaderTranslations);
    return translations[header] || header;
}
/**
 * PasswordXP CSV importer
 */
class bw_PasswordXPCsvImporter extends bw_base_importer_BaseImporter {
    /**
     * Parses the PasswordXP CSV data.
     * @param data
     */
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true, {
            skipEmptyLines: true,
            transformHeader: bw_translateIntoEnglishHeaders,
        });
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        // If the first row (header check) does not contain the column "Title", then the data is invalid (no translation found)
        if (!results[0].Title) {
            result.success = false;
            return Promise.resolve(result);
        }
        let currentFolderName = "";
        results.forEach((row) => {
            // Skip rows starting with '>>>' as they indicate items following have no folder assigned to them
            if (row.Title == ">>>") {
                return;
            }
            const title = row.Title;
            // If the title is in the format [title], then it is a folder name
            if (title.startsWith("[") && title.endsWith("]")) {
                currentFolderName = title.startsWith("/")
                    ? title.replace("/", "")
                    : title.substring(1, title.length - 1);
                return;
            }
            if (!bw_utils_Utils.isNullOrWhitespace(currentFolderName)) {
                this.processFolder(result, currentFolderName);
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(row.Title);
            cipher.login.username = this.getValueOrDefault(row.Username);
            cipher.notes = this.getValueOrDefault(row.Description);
            cipher.login.uris = this.makeUriArray(row.URL);
            cipher.login.password = this.getValueOrDefault(row.Password);
            this.importUnmappedFields(cipher, row, bw_passwordxp_csv_importer_mappedColumns);
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    importUnmappedFields(cipher, row, mappedValues) {
        const unmappedFields = Object.keys(row).filter((x) => !mappedValues.has(x));
        unmappedFields.forEach((key) => {
            const item = row;
            this.processKvp(cipher, key, item[key]);
        });
    }
}

;// ../../libs/importer/src/importers/protonpass/protonpass-import-utils.ts
function bw_processNames(fullname, firstname, middlename, lastname) {
    let mappedFirstName = firstname;
    let mappedMiddleName = middlename;
    let mappedLastName = lastname;
    if (fullname) {
        const parts = fullname.trim().split(/\s+/);
        // Assign parts to first, middle, and last name based on the number of parts
        mappedFirstName = parts[0] || firstname;
        mappedLastName = parts.length > 1 ? parts[parts.length - 1] : lastname;
        mappedMiddleName = parts.length > 2 ? parts.slice(1, -1).join(" ") : middlename;
    }
    return { mappedFirstName, mappedMiddleName, mappedLastName };
}

;// ../../libs/importer/src/importers/protonpass/types/protonpass-json-type.ts
var bw_ProtonPassItemState;
(function (ProtonPassItemState) {
    ProtonPassItemState[ProtonPassItemState["ACTIVE"] = 1] = "ACTIVE";
    ProtonPassItemState[ProtonPassItemState["TRASHED"] = 2] = "TRASHED";
})(bw_ProtonPassItemState || (bw_ProtonPassItemState = {}));

;// ../../libs/importer/src/importers/protonpass/protonpass-json-importer.ts








class bw_ProtonPassJsonImporter extends bw_base_importer_BaseImporter {
    constructor(i18nService) {
        super();
        this.i18nService = i18nService;
        this.mappedIdentityItemKeys = [
            "fullName",
            "firstName",
            "middleName",
            "lastName",
            "email",
            "phoneNumber",
            "company",
            "socialSecurityNumber",
            "passportNumber",
            "licenseNumber",
            "organization",
            "streetAddress",
            "floor",
            "county",
            "city",
            "stateOrProvince",
            "zipOrPostalCode",
            "countryOrRegion",
        ];
        this.identityItemExtraFieldsKeys = [
            "extraPersonalDetails",
            "extraAddressDetails",
            "extraContactDetails",
            "extraWorkDetails",
            "extraSections",
        ];
    }
    processIdentityItemUnmappedAndExtraFields(cipher, identityItem) {
        Object.keys(identityItem).forEach((key) => {
            if (!this.mappedIdentityItemKeys.includes(key) &&
                !this.identityItemExtraFieldsKeys.includes(key)) {
                this.processKvp(cipher, key, identityItem[key]);
                return;
            }
            if (this.identityItemExtraFieldsKeys.includes(key)) {
                if (key !== "extraSections") {
                    const extraFields = identityItem[key];
                    extraFields === null || extraFields === void 0 ? void 0 : extraFields.forEach((extraField) => {
                        this.processKvp(cipher, extraField.fieldName, extraField.data.content, extraField.type === "hidden" ? bw_FieldType.Hidden : bw_FieldType.Text);
                    });
                }
                else {
                    const extraSections = identityItem[key];
                    extraSections === null || extraSections === void 0 ? void 0 : extraSections.forEach((extraSection) => {
                        var _a;
                        (_a = extraSection.sectionFields) === null || _a === void 0 ? void 0 : _a.forEach((extraField) => {
                            this.processKvp(cipher, extraField.fieldName, extraField.data.content, extraField.type === "hidden" ? bw_FieldType.Hidden : bw_FieldType.Text);
                        });
                    });
                }
            }
        });
    }
    parse(data) {
        var _a, _b;
        const result = new bw_import_result_ImportResult();
        const results = JSON.parse(data);
        if (results == null || results.vaults == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        if (results.encrypted) {
            result.success = false;
            result.errorMessage = this.i18nService.t("unsupportedEncryptedImport");
            return Promise.resolve(result);
        }
        for (const [, vault] of Object.entries(results.vaults)) {
            for (const item of vault.items) {
                if (item.state == bw_ProtonPassItemState.TRASHED) {
                    continue;
                }
                const cipher = this.initLoginCipher();
                cipher.name = this.getValueOrDefault(item.data.metadata.name, "--");
                cipher.notes = this.getValueOrDefault(item.data.metadata.note);
                cipher.favorite = item.pinned;
                switch (item.data.type) {
                    case "login": {
                        const loginContent = item.data.content;
                        cipher.login.uris = this.makeUriArray(loginContent.urls);
                        cipher.login.username = this.getValueOrDefault(loginContent.itemUsername);
                        // if the cipher has no username then the email is used as the username
                        if (cipher.login.username == null) {
                            cipher.login.username = this.getValueOrDefault(loginContent.itemEmail);
                        }
                        else {
                            this.processKvp(cipher, "email", loginContent.itemEmail);
                        }
                        cipher.login.password = this.getValueOrDefault(loginContent.password);
                        cipher.login.totp = this.getValueOrDefault(loginContent.totpUri);
                        for (const extraField of item.data.extraFields) {
                            this.processKvp(cipher, extraField.fieldName, extraField.type == "totp" ? extraField.data.totpUri : extraField.data.content, extraField.type == "text" ? bw_FieldType.Text : bw_FieldType.Hidden);
                        }
                        break;
                    }
                    case "note":
                        cipher.type = bw_CipherType.SecureNote;
                        cipher.secureNote = new bw_SecureNoteView();
                        cipher.secureNote.type = bw_SecureNoteType.Generic;
                        break;
                    case "creditCard": {
                        const creditCardContent = item.data.content;
                        cipher.type = bw_CipherType.Card;
                        cipher.card = new bw_CardView();
                        cipher.card.cardholderName = this.getValueOrDefault(creditCardContent.cardholderName);
                        cipher.card.number = this.getValueOrDefault(creditCardContent.number);
                        cipher.card.brand = bw_CardView.getCardBrandByPatterns(creditCardContent.number);
                        cipher.card.code = this.getValueOrDefault(creditCardContent.verificationNumber);
                        if (!this.isNullOrWhitespace(creditCardContent.expirationDate)) {
                            cipher.card.expMonth = creditCardContent.expirationDate.substring(5, 7);
                            cipher.card.expMonth = cipher.card.expMonth.replace(/^0+/, "");
                            cipher.card.expYear = creditCardContent.expirationDate.substring(0, 4);
                        }
                        if (!this.isNullOrWhitespace(creditCardContent.pin)) {
                            this.processKvp(cipher, "PIN", creditCardContent.pin, bw_FieldType.Hidden);
                        }
                        break;
                    }
                    case "identity": {
                        const identityContent = item.data.content;
                        cipher.type = bw_CipherType.Identity;
                        cipher.identity = new bw_IdentityView();
                        const { mappedFirstName, mappedMiddleName, mappedLastName } = bw_processNames(this.getValueOrDefault(identityContent.fullName), this.getValueOrDefault(identityContent.firstName), this.getValueOrDefault(identityContent.middleName), this.getValueOrDefault(identityContent.lastName));
                        cipher.identity.firstName = mappedFirstName;
                        cipher.identity.middleName = mappedMiddleName;
                        cipher.identity.lastName = mappedLastName;
                        cipher.identity.email = this.getValueOrDefault(identityContent.email);
                        cipher.identity.phone = this.getValueOrDefault(identityContent.phoneNumber);
                        cipher.identity.company = this.getValueOrDefault(identityContent.company);
                        cipher.identity.ssn = this.getValueOrDefault(identityContent.socialSecurityNumber);
                        cipher.identity.passportNumber = this.getValueOrDefault(identityContent.passportNumber);
                        cipher.identity.licenseNumber = this.getValueOrDefault(identityContent.licenseNumber);
                        const address3 = `${(_a = identityContent.floor) !== null && _a !== void 0 ? _a : ""} ${(_b = identityContent.county) !== null && _b !== void 0 ? _b : ""}`.trim();
                        cipher.identity.address1 = this.getValueOrDefault(identityContent.organization);
                        cipher.identity.address2 = this.getValueOrDefault(identityContent.streetAddress);
                        cipher.identity.address3 = this.getValueOrDefault(address3);
                        cipher.identity.city = this.getValueOrDefault(identityContent.city);
                        cipher.identity.state = this.getValueOrDefault(identityContent.stateOrProvince);
                        cipher.identity.postalCode = this.getValueOrDefault(identityContent.zipOrPostalCode);
                        cipher.identity.country = this.getValueOrDefault(identityContent.countryOrRegion);
                        this.processIdentityItemUnmappedAndExtraFields(cipher, identityContent);
                        for (const extraField of item.data.extraFields) {
                            this.processKvp(cipher, extraField.fieldName, extraField.data.content, extraField.type === "hidden" ? bw_FieldType.Hidden : bw_FieldType.Text);
                        }
                        break;
                    }
                    default:
                        continue;
                }
                this.processFolder(result, vault.name);
                this.cleanupCipher(cipher);
                result.ciphers.push(cipher);
            }
        }
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/psono/psono-json-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_PsonoJsonImporter extends bw_base_importer_BaseImporter {
    constructor() {
        super(...arguments);
        this.WEBSITE_mappedValues = new Set([
            "type",
            "name",
            "website_password_title",
            "website_password_notes",
            "website_password_username",
            "website_password_password",
            "website_password_url",
            "autosubmit",
            "website_password_auto_submit",
            "urlfilter",
            "website_password_url_filter",
        ]);
        this.APP_PWD_mappedValues = new Set([
            "type",
            "name",
            "application_password_title",
            "application_password_notes",
            "application_password_username",
            "application_password_password",
        ]);
        this.BOOKMARK_mappedValues = new Set([
            "type",
            "name",
            "bookmark_title",
            "bookmark_notes",
            "bookmark_url",
        ]);
        this.NOTES_mappedValues = new Set(["type", "name", "note_title", "note_notes"]);
        this.TOTP_mappedValues = new Set(["type", "name", "totp_title", "totp_notes", "totp_code"]);
        this.ENV_VARIABLES_mappedValues = new Set([
            "type",
            "name",
            "environment_variables_title",
            "environment_variables_notes",
            "environment_variables_variables",
        ]);
        this.GPG_mappedValues = new Set([
            "type",
            "name",
            "mail_gpg_own_key_title",
            "mail_gpg_own_key_public",
            "mail_gpg_own_key_name",
            "mail_gpg_own_key_email",
            "mail_gpg_own_key_private",
        ]);
    }
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const psonoExport = JSON.parse(data);
        if (psonoExport == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        this.parseFolders(result, psonoExport.folders);
        this.handleItemParsing(result, psonoExport.items);
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    parseFolders(result, folders, parentName) {
        if (folders == null || folders.length === 0) {
            return;
        }
        folders.forEach((folder) => {
            const folderHasItems = folder.items != null && folder.items.length > 0;
            const folderHasSubfolders = folder.folders != null && folder.folders.length > 0;
            if (!folderHasItems && !folderHasSubfolders) {
                return;
            }
            if (!bw_utils_Utils.isNullOrWhitespace(parentName)) {
                folder.name = parentName + "/" + folder.name;
            }
            if (folderHasSubfolders) {
                this.parseFolders(result, folder.folders, folder.name);
            }
            if (!folderHasItems) {
                this.processFolder(result, folder.name, folderHasItems);
            }
            else {
                this.handleItemParsing(result, folder.items, folder.name);
            }
        });
    }
    handleItemParsing(result, items, folderName) {
        if (items == null || items.length === 0) {
            return;
        }
        items.forEach((record) => {
            const cipher = this.parsePsonoItem(record);
            this.processFolder(result, folderName, true);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
    }
    parsePsonoItem(item) {
        const cipher = this.initLoginCipher();
        switch (item.type) {
            case "website_password":
                this.parseWebsiteLogins(item, cipher);
                break;
            case "application_password":
                this.parseApplicationPasswords(item, cipher);
                break;
            case "environment_variables":
                this.parseEnvironmentVariables(item, cipher);
                break;
            case "totp":
                this.parseTOTP(item, cipher);
                break;
            case "bookmark":
                this.parseBookmarks(item, cipher);
                break;
            // Skipping this until we can save GPG into notes/custom fields
            // case "mail_gpg_own_key":
            //   this.parseGPG(item, cipher);
            //   break;
            case "note":
                this.parseNotes(item, cipher);
                break;
            default:
                break;
        }
        return cipher;
    }
    parseWebsiteLogins(entry, cipher) {
        var _a;
        if (entry == null || entry.type != "website_password") {
            return;
        }
        cipher.name = entry.website_password_title;
        cipher.notes = entry.website_password_notes;
        cipher.login.username = entry.website_password_username;
        cipher.login.password = entry.website_password_password;
        cipher.login.uris = this.makeUriArray(entry.website_password_url);
        this.processKvp(cipher, "website_password_auto_submit", (_a = entry.website_password_auto_submit) === null || _a === void 0 ? void 0 : _a.toString(), bw_FieldType.Boolean);
        this.processKvp(cipher, "website_password_url_filter", entry.website_password_url_filter);
        this.importUnmappedFields(cipher, entry, this.WEBSITE_mappedValues);
    }
    parseApplicationPasswords(entry, cipher) {
        if (entry == null || entry.type != "application_password") {
            return;
        }
        cipher.name = entry.application_password_title;
        cipher.notes = entry.application_password_notes;
        cipher.login.username = entry.application_password_username;
        cipher.login.password = entry.application_password_password;
        this.importUnmappedFields(cipher, entry, this.APP_PWD_mappedValues);
    }
    parseBookmarks(entry, cipher) {
        if (entry == null || entry.type != "bookmark") {
            return;
        }
        cipher.name = entry.bookmark_title;
        cipher.notes = entry.bookmark_notes;
        cipher.login.uris = this.makeUriArray(entry.bookmark_url);
        this.importUnmappedFields(cipher, entry, this.BOOKMARK_mappedValues);
    }
    parseNotes(entry, cipher) {
        if (entry == null || entry.type != "note") {
            return;
        }
        cipher.type = bw_CipherType.SecureNote;
        cipher.secureNote = new bw_SecureNoteView();
        cipher.secureNote.type = bw_SecureNoteType.Generic;
        cipher.name = entry.note_title;
        cipher.notes = entry.note_notes;
        this.importUnmappedFields(cipher, entry, this.NOTES_mappedValues);
    }
    parseTOTP(entry, cipher) {
        if (entry == null || entry.type != "totp") {
            return;
        }
        cipher.name = entry.totp_title;
        cipher.notes = entry.totp_notes;
        cipher.login.totp = entry.totp_code;
        this.importUnmappedFields(cipher, entry, this.TOTP_mappedValues);
    }
    parseEnvironmentVariables(entry, cipher) {
        if (entry == null || entry.type != "environment_variables") {
            return;
        }
        cipher.type = bw_CipherType.SecureNote;
        cipher.secureNote = new bw_SecureNoteView();
        cipher.secureNote.type = bw_SecureNoteType.Generic;
        cipher.name = entry.environment_variables_title;
        cipher.notes = entry.environment_variables_notes;
        entry.environment_variables_variables.forEach((KvPair) => {
            this.processKvp(cipher, KvPair.key, KvPair.value);
        });
        this.importUnmappedFields(cipher, entry, this.ENV_VARIABLES_mappedValues);
    }
    parseGPG(entry, cipher) {
        if (entry == null || entry.type != "mail_gpg_own_key") {
            return;
        }
        cipher.type = bw_CipherType.SecureNote;
        cipher.secureNote = new bw_SecureNoteView();
        cipher.secureNote.type = bw_SecureNoteType.Generic;
        cipher.name = entry.mail_gpg_own_key_title;
        cipher.notes = entry.mail_gpg_own_key_public;
        this.processKvp(cipher, "mail_gpg_own_key_name", entry.mail_gpg_own_key_name);
        this.processKvp(cipher, "mail_gpg_own_key_email", entry.mail_gpg_own_key_email);
        this.processKvp(cipher, "mail_gpg_own_key_private", entry.mail_gpg_own_key_private, bw_FieldType.Hidden);
        this.importUnmappedFields(cipher, entry, this.GPG_mappedValues);
    }
    importUnmappedFields(cipher, entry, mappedValues) {
        const unmappedFields = Object.keys(entry).filter((x) => !mappedValues.has(x));
        unmappedFields.forEach((key) => {
            const item = entry;
            this.processKvp(cipher, key, item[key].toString());
        });
    }
}

;// ../../libs/importer/src/importers/remembear-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_RememBearCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.trash === "true") {
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.name);
            cipher.notes = this.getValueOrDefault(value.notes);
            if (value.type === "LoginItem") {
                cipher.login.uris = this.makeUriArray(value.website);
                cipher.login.password = this.getValueOrDefault(value.password);
                cipher.login.username = this.getValueOrDefault(value.username);
            }
            else if (value.type === "CreditCardItem") {
                cipher.type = bw_CipherType.Card;
                cipher.card = new bw_CardView();
                cipher.card.cardholderName = this.getValueOrDefault(value.cardholder);
                cipher.card.number = this.getValueOrDefault(value.number);
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                cipher.card.code = this.getValueOrDefault(value.verification);
                try {
                    const expMonth = this.getValueOrDefault(value.expiryMonth);
                    if (expMonth != null) {
                        const expMonthNumber = parseInt(expMonth, null);
                        if (expMonthNumber != null && expMonthNumber >= 1 && expMonthNumber <= 12) {
                            cipher.card.expMonth = expMonthNumber.toString();
                        }
                    }
                }
                catch (_a) {
                    // Ignore error
                }
                try {
                    const expYear = this.getValueOrDefault(value.expiryYear);
                    if (expYear != null) {
                        const expYearNumber = parseInt(expYear, null);
                        if (expYearNumber != null) {
                            cipher.card.expYear = expYearNumber.toString();
                        }
                    }
                }
                catch (_b) {
                    // Ignore error
                }
                const pin = this.getValueOrDefault(value.pin);
                if (pin != null) {
                    this.processKvp(cipher, "PIN", pin);
                }
                const zip = this.getValueOrDefault(value.zipCode);
                if (zip != null) {
                    this.processKvp(cipher, "Zip Code", zip);
                }
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/roboform-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_RoboFormCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        let i = 1;
        results.forEach((value) => {
            const folder = !this.isNullOrWhitespace(value.Folder) && value.Folder.startsWith("/")
                ? value.Folder.replace("/", "")
                : value.Folder;
            const folderName = !this.isNullOrWhitespace(folder) ? folder : null;
            this.processFolder(result, folderName);
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValueOrDefault(value.Note);
            cipher.name = this.getValueOrDefault(value.Name, "--");
            cipher.login.username = this.getValueOrDefault(value.Login);
            cipher.login.password = this.getValueOrDefault(value.Pwd);
            cipher.login.uris = this.makeUriArray(value.Url);
            if (!this.isNullOrWhitespace(value.Rf_fields)) {
                let fields = [value.Rf_fields];
                if (value.__parsed_extra != null && value.__parsed_extra.length > 0) {
                    fields = fields.concat(value.__parsed_extra);
                }
                fields.forEach((field) => {
                    const parts = field.split(":");
                    if (parts.length < 3) {
                        return;
                    }
                    const key = parts[0] === "-no-name-" ? null : parts[0];
                    const val = parts.length === 4 && parts[2] === "rck" ? parts[1] : parts[2];
                    this.processKvp(cipher, key, val);
                });
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            if (i === results.length &&
                cipher.name === "--" &&
                this.isNullOrWhitespace(cipher.login.password)) {
                return;
            }
            result.ciphers.push(cipher);
            i++;
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/safari-csv-importer.ts


class bw_SafariCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            var _a;
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.Title, "--");
            cipher.login.username = this.getValueOrDefault(value.Username);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.uris = this.makeUriArray((_a = value.Url) !== null && _a !== void 0 ? _a : value.URL);
            cipher.login.totp = this.getValueOrDefault(value.OTPAuth);
            cipher.notes = this.getValueOrDefault(value.Notes);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/safeincloud-xml-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore





class bw_SafeInCloudXmlImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const doc = this.parseXml(data);
        if (doc == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        const db = doc.querySelector("database");
        if (db == null) {
            result.errorMessage = "Missing `database` node.";
            result.success = false;
            return Promise.resolve(result);
        }
        const foldersMap = new Map();
        Array.from(doc.querySelectorAll("database > label")).forEach((labelEl) => {
            const name = labelEl.getAttribute("name");
            const id = labelEl.getAttribute("id");
            if (!this.isNullOrWhitespace(name) && !this.isNullOrWhitespace(id)) {
                foldersMap.set(id, result.folders.length);
                const folder = new bw_FolderView();
                folder.name = name;
                result.folders.push(folder);
            }
        });
        Array.from(doc.querySelectorAll("database > card")).forEach((cardEl) => {
            if (cardEl.getAttribute("template") === "true" || cardEl.getAttribute("deleted") === "true") {
                return;
            }
            const labelIdEl = this.querySelectorDirectChild(cardEl, "label_id");
            if (labelIdEl != null) {
                const labelId = labelIdEl.textContent;
                if (!this.isNullOrWhitespace(labelId) && foldersMap.has(labelId)) {
                    result.folderRelationships.push([result.ciphers.length, foldersMap.get(labelId)]);
                }
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(cardEl.getAttribute("title"), "--");
            if (cardEl.getAttribute("star") === "true") {
                cipher.favorite = true;
            }
            const cardType = cardEl.getAttribute("type");
            if (cardType === "note") {
                cipher.type = bw_CipherType.SecureNote;
                cipher.secureNote = new bw_SecureNoteView();
                cipher.secureNote.type = bw_SecureNoteType.Generic;
            }
            else {
                Array.from(this.querySelectorAllDirectChild(cardEl, "field")).forEach((fieldEl) => {
                    const text = fieldEl.textContent;
                    if (this.isNullOrWhitespace(text)) {
                        return;
                    }
                    const name = fieldEl.getAttribute("name");
                    const fieldType = this.getValueOrDefault(fieldEl.getAttribute("type"), "").toLowerCase();
                    if (fieldType === "login") {
                        cipher.login.username = text;
                    }
                    else if (fieldType === "password" || fieldType === "secret") {
                        // safeInCloud allows for more than one password. we just insert them here and find the one used as password later
                        this.processKvp(cipher, name, text, bw_FieldType.Hidden);
                    }
                    else if (fieldType === "one_time_password") {
                        cipher.login.totp = text;
                    }
                    else if (fieldType === "notes") {
                        cipher.notes += text + "\n";
                    }
                    else if (fieldType === "weblogin" || fieldType === "website") {
                        cipher.login.uris.push(...this.makeUriArray(text));
                    }
                    else {
                        this.processKvp(cipher, name, text);
                    }
                });
            }
            Array.from(this.querySelectorAllDirectChild(cardEl, "notes")).forEach((notesEl) => {
                cipher.notes += notesEl.textContent + "\n";
            });
            this.setPassword(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    // Choose a password from all passwords. Take one that has password in its name, or the first one if there is no such entry
    // if its name is password, we can safely remove it form the fields. otherwise, it would maybe be best to keep it as a hidden field
    setPassword(cipher) {
        const candidates = cipher.fields.filter((field) => field.type === bw_FieldType.Hidden);
        if (!candidates.length) {
            return;
        }
        let choice;
        for (const field of candidates) {
            if (this.passwordFieldNames.includes(field.name.toLowerCase())) {
                choice = field;
                cipher.fields = cipher.fields.filter((f) => f !== choice);
                break;
            }
        }
        if (!choice) {
            choice = candidates[0];
        }
        cipher.login.password = choice.value;
    }
}

;// ../../libs/importer/src/importers/saferpass-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_SaferPassCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(this.nameFromUrl(value.url), "--");
            cipher.notes = this.getValueOrDefault(value.notes);
            cipher.login.username = this.getValueOrDefault(value.username);
            cipher.login.password = this.getValueOrDefault(value.password);
            cipher.login.uris = this.makeUriArray(value.url);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/securesafe-csv-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_SecureSafeCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        // The url field can be in different case formats.
        const urlField = Object.keys(results[0]).find((k) => /url/i.test(k));
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.Title);
            cipher.notes = this.getValueOrDefault(value.Comment);
            cipher.login.uris = this.makeUriArray(value[urlField]);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.username = this.getValueOrDefault(value.Username);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/splashid-csv-importer.ts


class bw_SplashIdCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length < 3) {
                return;
            }
            this.processFolder(result, this.getValueOrDefault(value[value.length - 1]));
            const cipher = this.initLoginCipher();
            cipher.notes = this.getValueOrDefault(value[value.length - 2], "");
            cipher.name = this.getValueOrDefault(value[1], "--");
            if (value[0] === "Web Logins" || value[0] === "Servers" || value[0] === "Email Accounts") {
                cipher.login.username = this.getValueOrDefault(value[2]);
                cipher.login.password = this.getValueOrDefault(value[3]);
                cipher.login.uris = this.makeUriArray(value[4]);
                this.parseFieldsToNotes(cipher, 5, value);
            }
            else {
                this.parseFieldsToNotes(cipher, 2, value);
            }
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    parseFieldsToNotes(cipher, startIndex, value) {
        // last 3 rows do not get parsed
        for (let i = startIndex; i < value.length - 3; i++) {
            if (this.isNullOrWhitespace(value[i])) {
                continue;
            }
            cipher.notes += value[i] + "\n";
        }
    }
}

;// ../../libs/importer/src/importers/stickypassword-xml-importer.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_StickyPasswordXmlImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const doc = this.parseXml(data);
        if (doc == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        const loginNodes = doc.querySelectorAll("root > Database > Logins > Login");
        Array.from(loginNodes).forEach((loginNode) => {
            const accountId = loginNode.getAttribute("ID");
            if (this.isNullOrWhitespace(accountId)) {
                return;
            }
            const usernameText = loginNode.getAttribute("Name");
            const passwordText = loginNode.getAttribute("Password");
            let titleText = null;
            let linkText = null;
            let notesText = null;
            let groupId = null;
            let groupText = null;
            const accountLogin = doc.querySelector("root > Database > Accounts > Account > " +
                'LoginLinks > Login[SourceLoginID="' +
                accountId +
                '"]');
            if (accountLogin != null) {
                const account = accountLogin.parentElement.parentElement;
                if (account != null) {
                    titleText = account.getAttribute("Name");
                    linkText = account.getAttribute("Link");
                    groupId = account.getAttribute("ParentID");
                    notesText = account.getAttribute("Comments");
                    if (!this.isNullOrWhitespace(notesText)) {
                        notesText = notesText.split("/n").join("\n");
                    }
                }
            }
            if (!this.isNullOrWhitespace(groupId)) {
                groupText = this.buildGroupText(doc, groupId, "");
                this.processFolder(result, groupText);
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(titleText, "--");
            cipher.notes = this.getValueOrDefault(notesText);
            cipher.login.username = this.getValueOrDefault(usernameText);
            cipher.login.password = this.getValueOrDefault(passwordText);
            cipher.login.uris = this.makeUriArray(linkText);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    buildGroupText(doc, groupId, groupText) {
        const group = doc.querySelector('root > Database > Groups > Group[ID="' + groupId + '"]');
        if (group == null) {
            return groupText;
        }
        if (!this.isNullOrWhitespace(groupText)) {
            groupText = "/" + groupText;
        }
        groupText = group.getAttribute("Name") + groupText;
        return this.buildGroupText(doc, group.getAttribute("ParentID"), groupText);
    }
}

;// ../../libs/importer/src/importers/truekey-csv-importer.ts





const bw_PropertiesToIgnore = [
    "kind",
    "autologin",
    "favorite",
    "hexcolor",
    "protectedwithpassword",
    "subdomainonly",
    "type",
    "tk_export_version",
    "note",
    "title",
    "document_content",
];
class bw_TrueKeyCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.favorite = this.getValueOrDefault(value.favorite, "").toLowerCase() === "true";
            cipher.name = this.getValueOrDefault(value.name, "--");
            cipher.notes = this.getValueOrDefault(value.memo, "");
            cipher.login.username = this.getValueOrDefault(value.login);
            cipher.login.password = this.getValueOrDefault(value.password);
            cipher.login.uris = this.makeUriArray(value.url);
            if (value.kind !== "login") {
                cipher.name = this.getValueOrDefault(value.title, "--");
                cipher.notes = this.getValueOrDefault(value.note, "");
            }
            if (value.kind === "cc") {
                cipher.type = bw_CipherType.Card;
                cipher.card = new bw_CardView();
                cipher.card.cardholderName = this.getValueOrDefault(value.cardholder);
                cipher.card.number = this.getValueOrDefault(value.number);
                cipher.card.brand = bw_CardView.getCardBrandByPatterns(cipher.card.number);
                if (!this.isNullOrWhitespace(value.expiryDate)) {
                    try {
                        const expDate = new Date(value.expiryDate);
                        cipher.card.expYear = expDate.getFullYear().toString();
                        cipher.card.expMonth = (expDate.getMonth() + 1).toString();
                    }
                    catch (_a) {
                        // Ignore error
                    }
                }
            }
            else if (value.kind !== "login") {
                cipher.type = bw_CipherType.SecureNote;
                cipher.secureNote = new bw_SecureNoteView();
                cipher.secureNote.type = bw_SecureNoteType.Generic;
                if (!this.isNullOrWhitespace(cipher.notes)) {
                    cipher.notes = this.getValueOrDefault(value.document_content, "");
                }
                for (const property in value) {
                    if (value.hasOwnProperty(property) && // eslint-disable-line
                        bw_PropertiesToIgnore.indexOf(property.toLowerCase()) < 0 &&
                        !this.isNullOrWhitespace(value[property])) {
                        this.processKvp(cipher, property, value[property]);
                    }
                }
            }
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/upm-csv-importer.ts


class bw_UpmCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, false);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (value.length !== 5) {
                return;
            }
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value[0], "--");
            cipher.notes = this.getValueOrDefault(value[4]);
            cipher.login.username = this.getValueOrDefault(value[1]);
            cipher.login.password = this.getValueOrDefault(value[2]);
            cipher.login.uris = this.makeUriArray(value[3]);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/yoti-csv-importer.ts


class bw_YotiCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            const cipher = this.initLoginCipher();
            cipher.name = this.getValueOrDefault(value.Name, "--");
            cipher.login.username = this.getValueOrDefault(value["User name"]);
            cipher.login.password = this.getValueOrDefault(value.Password);
            cipher.login.uris = this.makeUriArray(value.URL);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        result.success = true;
        return Promise.resolve(result);
    }
}

;// ../../libs/importer/src/importers/zohovault-csv-importer.ts


class bw_ZohoVaultCsvImporter extends bw_base_importer_BaseImporter {
    parse(data) {
        const result = new bw_import_result_ImportResult();
        const results = this.parseCsv(data, true);
        if (results == null) {
            result.success = false;
            return Promise.resolve(result);
        }
        results.forEach((value) => {
            if (this.isNullOrWhitespace(value["Password Name"]) &&
                this.isNullOrWhitespace(value["Secret Name"])) {
                return;
            }
            this.processFolder(result, this.getValueOrDefault(value["Folder Name"]));
            const cipher = this.initLoginCipher();
            cipher.favorite = this.getValueOrDefault(value.Favorite, "0") === "1";
            cipher.notes = this.getValueOrDefault(value.Notes);
            cipher.name = this.getValueOrDefault(value["Password Name"], this.getValueOrDefault(value["Secret Name"], "--"));
            cipher.login.uris = this.makeUriArray(this.getValueOrDefault(value["Password URL"], this.getValueOrDefault(value["Secret URL"])));
            cipher.login.totp = this.getValueOrDefault(value["login_totp"]);
            this.parseData(cipher, value.SecretData);
            this.parseData(cipher, value.CustomData);
            this.convertToNoteIfNeeded(cipher);
            this.cleanupCipher(cipher);
            result.ciphers.push(cipher);
        });
        if (this.organization) {
            this.moveFoldersToCollections(result);
        }
        result.success = true;
        return Promise.resolve(result);
    }
    parseData(cipher, data) {
        if (this.isNullOrWhitespace(data)) {
            return;
        }
        const dataLines = this.splitNewLine(data);
        dataLines.forEach((line) => {
            const delimPosition = line.indexOf(":");
            if (delimPosition < 0) {
                return;
            }
            const field = line.substring(0, delimPosition);
            const value = line.length > delimPosition ? line.substring(delimPosition + 1) : null;
            if (this.isNullOrWhitespace(field) ||
                this.isNullOrWhitespace(value) ||
                field === "SecretType") {
                return;
            }
            const fieldLower = field.toLowerCase();
            if (cipher.login.username == null && this.usernameFieldNames.indexOf(fieldLower) > -1) {
                cipher.login.username = value;
            }
            else if (cipher.login.password == null &&
                this.passwordFieldNames.indexOf(fieldLower) > -1) {
                cipher.login.password = value;
            }
            else {
                this.processKvp(cipher, field, value);
            }
        });
    }
}

;// ../../libs/importer/src/importers/index.ts






















































;// ../../libs/importer/src/models/import-options.ts
const bw_featuredImportOptions = [
    { id: "bitwardenjson", name: "Bitwarden (json)" },
    { id: "bitwardencsv", name: "Bitwarden (csv)" },
    { id: "chromecsv", name: "Chrome (csv)" },
    { id: "dashlanecsv", name: "Dashlane (csv)" },
    { id: "firefoxcsv", name: "Firefox (csv)" },
    { id: "keepass2xml", name: "KeePass 2 (xml)" },
    { id: "lastpasscsv", name: "LastPass" },
    { id: "safaricsv", name: "Safari and macOS (csv)" },
    { id: "1password1pux", name: "1Password (1pux/json)" },
];
const bw_regularImportOptions = [
    { id: "keepassxcsv", name: "KeePassX (csv)" },
    { id: "1password1pif", name: "1Password (1pif)" },
    { id: "1passwordwincsv", name: "1Password 6 and 7 Windows (csv)" },
    { id: "1passwordmaccsv", name: "1Password 6 and 7 Mac (csv)" },
    { id: "dashlanejson", name: "Dashlane (json)" },
    { id: "roboformcsv", name: "RoboForm (csv)" },
    { id: "keepercsv", name: "Keeper (csv)" },
    // Temporarily remove this option for the Feb release
    // { id: "keeperjson", name: "Keeper (json)" },
    { id: "enpasscsv", name: "Enpass (csv)" },
    { id: "enpassjson", name: "Enpass (json)" },
    { id: "protonpass", name: "ProtonPass (zip/json)" },
    { id: "safeincloudxml", name: "SafeInCloud (xml)" },
    { id: "pwsafexml", name: "Password Safe - pwsafe.org (xml)" },
    { id: "stickypasswordxml", name: "Sticky Password (xml)" },
    { id: "msecurecsv", name: "mSecure (csv)" },
    { id: "truekeycsv", name: "True Key (csv)" },
    { id: "passwordbossjson", name: "Password Boss (json)" },
    { id: "zohovaultcsv", name: "Zoho Vault (csv)" },
    { id: "splashidcsv", name: "SplashID (csv)" },
    { id: "passworddragonxml", name: "Password Dragon (xml)" },
    { id: "padlockcsv", name: "Padlock (csv)" },
    { id: "passboltcsv", name: "Passbolt (csv)" },
    { id: "clipperzhtml", name: "Clipperz (html)" },
    { id: "aviracsv", name: "Avira (csv)" },
    { id: "saferpasscsv", name: "SaferPass (csv)" },
    { id: "upmcsv", name: "Universal Password Manager (csv)" },
    { id: "ascendocsv", name: "Ascendo DataVault (csv)" },
    { id: "meldiumcsv", name: "Meldium (csv)" },
    { id: "passkeepcsv", name: "PassKeep (csv)" },
    { id: "operacsv", name: "Opera (csv)" },
    { id: "vivaldicsv", name: "Vivaldi (csv)" },
    { id: "gnomejson", name: "GNOME Passwords and Keys/Seahorse (json)" },
    { id: "blurcsv", name: "Blur (csv)" },
    { id: "passwordagentcsv", name: "Password Agent (csv)" },
    { id: "passpackcsv", name: "Passpack (csv)" },
    { id: "passmanjson", name: "Passman (json)" },
    { id: "avastcsv", name: "Avast Passwords (csv)" },
    { id: "avastjson", name: "Avast Passwords (json)" },
    { id: "fsecurefsk", name: "F-Secure KEY (fsk)" },
    { id: "kasperskytxt", name: "Kaspersky Password Manager (txt)" },
    { id: "remembearcsv", name: "RememBear (csv)" },
    { id: "passwordwallettxt", name: "PasswordWallet (txt)" },
    { id: "mykicsv", name: "Myki (csv)" },
    { id: "securesafecsv", name: "SecureSafe (csv)" },
    { id: "logmeoncecsv", name: "LogMeOnce (csv)" },
    { id: "blackberrycsv", name: "BlackBerry Password Keeper (csv)" },
    { id: "buttercupcsv", name: "Buttercup (csv)" },
    { id: "codebookcsv", name: "Codebook (csv)" },
    { id: "encryptrcsv", name: "Encryptr (csv)" },
    { id: "yoticsv", name: "Yoti (csv)" },
    { id: "nordpasscsv", name: "Nordpass (csv)" },
    { id: "psonojson", name: "Psono (json)" },
    { id: "passkyjson", name: "Passky (json)" },
    { id: "passwordxpcsv", name: "Password XP (csv)" },
    { id: "netwrixpasswordsecure", name: "Netwrix Password Secure (csv)" },
];

;// ../../libs/importer/src/services/import.service.ts
var bw_import_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore













class bw_ImportService {
    constructor(cipherService, folderService, importApiService, i18nService, collectionService, keyService, encryptService, pinService, accountService, sdkService) {
        this.cipherService = cipherService;
        this.folderService = folderService;
        this.importApiService = importApiService;
        this.i18nService = i18nService;
        this.collectionService = collectionService;
        this.keyService = keyService;
        this.encryptService = encryptService;
        this.pinService = pinService;
        this.accountService = accountService;
        this.sdkService = sdkService;
        this.featuredImportOptions = bw_featuredImportOptions;
        this.regularImportOptions = bw_regularImportOptions;
    }
    getImportOptions() {
        return this.featuredImportOptions.concat(this.regularImportOptions);
    }
    import(importer_1, fileContents_1) {
        return bw_import_service_awaiter(this, arguments, void 0, function* (importer, fileContents, organizationId = null, selectedImportTarget = null, canAccessImportExport) {
            let importResult;
            try {
                importResult = yield importer.parse(fileContents);
            }
            catch (error) {
                if (error instanceof SyntaxError) {
                    throw new Error(this.i18nService.t("importFormatError"));
                }
                throw error;
            }
            if (!importResult.success) {
                if (!bw_utils_Utils.isNullOrWhitespace(importResult.errorMessage)) {
                    throw new Error(importResult.errorMessage);
                }
                throw new Error(this.i18nService.t("importFormatError"));
            }
            if (importResult.folders.length === 0 && importResult.ciphers.length === 0) {
                throw new Error(this.i18nService.t("importNothingError"));
            }
            if (importResult.ciphers.length > 0) {
                const halfway = Math.floor(importResult.ciphers.length / 2);
                const last = importResult.ciphers.length - 1;
                if (this.badData(importResult.ciphers[0]) &&
                    this.badData(importResult.ciphers[halfway]) &&
                    this.badData(importResult.ciphers[last])) {
                    throw new Error(this.i18nService.t("importFormatError"));
                }
            }
            if (organizationId && !selectedImportTarget && !canAccessImportExport) {
                const hasUnassignedCollections = importResult.collectionRelationships.length < importResult.ciphers.length;
                if (hasUnassignedCollections) {
                    throw new Error(this.i18nService.t("importUnassignedItemsError"));
                }
            }
            try {
                yield this.setImportTarget(importResult, organizationId, selectedImportTarget);
                if (organizationId != null) {
                    yield this.handleOrganizationalImport(importResult, organizationId);
                }
                else {
                    yield this.handleIndividualImport(importResult);
                }
            }
            catch (error) {
                const errorResponse = new bw_ErrorResponse(error, 400);
                throw this.handleServerError(errorResponse, importResult);
            }
            return importResult;
        });
    }
    getImporter(format, promptForPassword_callback, organizationId = null) {
        if (promptForPassword_callback == null) {
            return null;
        }
        const importer = this.getImporterInstance(format, promptForPassword_callback);
        if (importer == null) {
            return null;
        }
        importer.organizationId = organizationId;
        return importer;
    }
    getImporterInstance(format, promptForPassword_callback) {
        if (format == null) {
            return null;
        }
        switch (format) {
            case "bitwardencsv":
                return new bw_BitwardenCsvImporter();
            case "bitwardenjson":
            case "bitwardenpasswordprotected":
                return new bw_BitwardenPasswordProtectedImporter(this.keyService, this.encryptService, this.i18nService, this.cipherService, this.pinService, this.accountService, promptForPassword_callback);
            case "lastpasscsv":
            case "passboltcsv":
                return new bw_LastPassCsvImporter();
            case "keepassxcsv":
                return new bw_KeePassXCsvImporter();
            case "aviracsv":
                return new bw_AviraCsvImporter();
            case "blurcsv":
                return new bw_BlurCsvImporter();
            case "safeincloudxml":
                return new bw_SafeInCloudXmlImporter();
            case "padlockcsv":
                return new bw_PadlockCsvImporter();
            case "keepass2xml":
                return new bw_KeePass2XmlImporter();
            case "chromecsv":
            case "operacsv":
            case "vivaldicsv":
                return new bw_ChromeCsvImporter();
            case "firefoxcsv":
                return new bw_FirefoxCsvImporter();
            case "upmcsv":
                return new bw_UpmCsvImporter();
            case "saferpasscsv":
                return new bw_SaferPassCsvImporter();
            case "safaricsv":
                return new bw_SafariCsvImporter();
            case "meldiumcsv":
                return new bw_MeldiumCsvImporter();
            case "1password1pif":
                return new bw_OnePassword1PifImporter();
            case "1password1pux":
                return new bw_OnePassword1PuxImporter();
            case "1passwordwincsv":
                return new bw_OnePasswordWinCsvImporter();
            case "1passwordmaccsv":
                return new bw_OnePasswordMacCsvImporter();
            case "keepercsv":
                return new bw_KeeperCsvImporter();
            // case "keeperjson":
            //   return new KeeperJsonImporter();
            case "passworddragonxml":
                return new bw_PasswordDragonXmlImporter();
            case "enpasscsv":
                return new bw_EnpassCsvImporter();
            case "enpassjson":
                return new bw_EnpassJsonImporter();
            case "pwsafexml":
                return new bw_PasswordSafeXmlImporter();
            case "dashlanecsv":
                return new bw_DashlaneCsvImporter();
            case "dashlanejson":
                return new bw_DashlaneJsonImporter();
            case "msecurecsv":
                return new bw_MSecureCsvImporter();
            case "stickypasswordxml":
                return new bw_StickyPasswordXmlImporter();
            case "truekeycsv":
                return new bw_TrueKeyCsvImporter();
            case "clipperzhtml":
                return new bw_ClipperzHtmlImporter();
            case "roboformcsv":
                return new bw_RoboFormCsvImporter();
            case "ascendocsv":
                return new bw_AscendoCsvImporter();
            case "passwordbossjson":
                return new bw_PasswordBossJsonImporter();
            case "zohovaultcsv":
                return new bw_ZohoVaultCsvImporter();
            case "splashidcsv":
                return new bw_SplashIdCsvImporter();
            case "passkeepcsv":
                return new bw_PassKeepCsvImporter();
            case "gnomejson":
                return new bw_GnomeJsonImporter();
            case "passwordagentcsv":
                return new bw_PasswordAgentCsvImporter();
            case "passpackcsv":
                return new bw_PasspackCsvImporter();
            case "passmanjson":
                return new bw_PassmanJsonImporter();
            case "avastcsv":
                return new bw_AvastCsvImporter();
            case "avastjson":
                return new bw_AvastJsonImporter();
            case "fsecurefsk":
                return new bw_FSecureFskImporter();
            case "kasperskytxt":
                return new bw_KasperskyTxtImporter();
            case "remembearcsv":
                return new bw_RememBearCsvImporter();
            case "passwordwallettxt":
                return new bw_PasswordWalletTxtImporter();
            case "mykicsv":
                return new bw_MykiCsvImporter();
            case "securesafecsv":
                return new bw_SecureSafeCsvImporter();
            case "logmeoncecsv":
                return new bw_LogMeOnceCsvImporter();
            case "blackberrycsv":
                return new bw_BlackBerryCsvImporter();
            case "buttercupcsv":
                return new bw_ButtercupCsvImporter();
            case "codebookcsv":
                return new bw_CodebookCsvImporter();
            case "encryptrcsv":
                return new bw_EncryptrCsvImporter();
            case "yoticsv":
                return new bw_YotiCsvImporter();
            case "nordpasscsv":
                return new bw_NordPassCsvImporter();
            case "psonojson":
                return new bw_PsonoJsonImporter();
            case "passkyjson":
                return new bw_PasskyJsonImporter();
            case "protonpass":
                return new bw_ProtonPassJsonImporter(this.i18nService);
            case "passwordxpcsv":
                return new bw_PasswordXPCsvImporter();
            case "netwrixpasswordsecure":
                return new bw_NetwrixPasswordSecureCsvImporter();
            default:
                return null;
        }
    }
    handleIndividualImport(importResult) {
        return bw_import_service_awaiter(this, void 0, void 0, function* () {
            const request = new bw_ImportCiphersRequest();
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
            for (let i = 0; i < importResult.ciphers.length; i++) {
                const c = yield this.cipherService.encrypt(importResult.ciphers[i], activeUserId);
                request.ciphers.push(new bw_CipherRequest(c));
            }
            const userKey = yield this.keyService.getUserKeyWithLegacySupport(activeUserId);
            if (importResult.folders != null) {
                for (let i = 0; i < importResult.folders.length; i++) {
                    const f = yield this.folderService.encrypt(importResult.folders[i], userKey);
                    request.folders.push(new bw_FolderWithIdRequest(f));
                }
            }
            if (importResult.folderRelationships != null) {
                importResult.folderRelationships.forEach((r) => request.folderRelationships.push(new bw_KvpRequest(r[0], r[1])));
            }
            return yield this.importApiService.postImportCiphers(request);
        });
    }
    handleOrganizationalImport(importResult, organizationId) {
        return bw_import_service_awaiter(this, void 0, void 0, function* () {
            const request = new bw_ImportOrganizationCiphersRequest();
            const activeUserId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$.pipe((0,bw_external_rxjs_namespaceObject.map)((a) => a === null || a === void 0 ? void 0 : a.id)));
            for (let i = 0; i < importResult.ciphers.length; i++) {
                importResult.ciphers[i].organizationId = organizationId;
                const c = yield this.cipherService.encrypt(importResult.ciphers[i], activeUserId);
                request.ciphers.push(new bw_CipherRequest(c));
            }
            if (importResult.collections != null) {
                for (let i = 0; i < importResult.collections.length; i++) {
                    importResult.collections[i].organizationId = organizationId;
                    const c = yield this.collectionService.encrypt(importResult.collections[i]);
                    request.collections.push(new bw_CollectionWithIdRequest(c));
                }
            }
            if (importResult.collectionRelationships != null) {
                importResult.collectionRelationships.forEach((r) => request.collectionRelationships.push(new bw_KvpRequest(r[0], r[1])));
            }
            return yield this.importApiService.postImportOrganizationCiphers(organizationId, request);
        });
    }
    badData(c) {
        return ((c.name == null || c.name === "--") &&
            c.type === bw_CipherType.Login &&
            c.login != null &&
            bw_utils_Utils.isNullOrWhitespace(c.login.password));
    }
    handleServerError(errorResponse, importResult) {
        if (errorResponse.validationErrors == null) {
            return new Error(errorResponse.message);
        }
        let errorMessage = "";
        Object.entries(errorResponse.validationErrors).forEach(([key, value], index) => {
            let item;
            let itemType;
            const i = Number(key.match(/[0-9]+/)[0]);
            switch (key.match(/^\w+/)[0]) {
                case "Ciphers":
                    item = importResult.ciphers[i];
                    itemType = bw_CipherType[item.type];
                    break;
                case "Folders":
                    item = importResult.folders[i];
                    itemType = "Folder";
                    break;
                case "Collections":
                    item = importResult.collections[i];
                    itemType = "Collection";
                    break;
                default:
                    return;
            }
            if (index > 0) {
                errorMessage += "\n\n";
            }
            if (itemType !== "Folder" && itemType !== "Collection") {
                errorMessage += "[" + (i + 1) + "] ";
            }
            errorMessage += "[" + itemType + '] "' + item.name + '": ' + value;
        });
        return new Error(errorMessage);
    }
    setImportTarget(importResult, organizationId, importTarget) {
        return bw_import_service_awaiter(this, void 0, void 0, function* () {
            if (!importTarget) {
                return;
            }
            if (organizationId) {
                if (!(importTarget instanceof bw_CollectionView)) {
                    throw new Error(this.i18nService.t("errorAssigningTargetCollection"));
                }
                const noCollectionRelationShips = [];
                importResult.ciphers.forEach((c, index) => {
                    if (!Array.isArray(importResult.collectionRelationships) ||
                        !importResult.collectionRelationships.some(([cipherPos]) => cipherPos === index)) {
                        noCollectionRelationShips.push([index, 0]);
                    }
                });
                const collections = [...importResult.collections];
                importResult.collections = [importTarget];
                collections.map((x) => {
                    const f = new bw_CollectionView();
                    f.name = `${importTarget.name}/${x.name}`;
                    importResult.collections.push(f);
                });
                const relationships = [...importResult.collectionRelationships];
                importResult.collectionRelationships = [...noCollectionRelationShips];
                relationships.map((x) => {
                    importResult.collectionRelationships.push([x[0], x[1] + 1]);
                });
                return;
            }
            if (!(importTarget instanceof bw_FolderView)) {
                throw new Error(this.i18nService.t("errorAssigningTargetFolder"));
            }
            const noFolderRelationShips = [];
            importResult.ciphers.forEach((c, index) => {
                if (bw_utils_Utils.isNullOrEmpty(c.folderId)) {
                    c.folderId = importTarget.id;
                    noFolderRelationShips.push([index, 0]);
                }
            });
            const folders = [...importResult.folders];
            importResult.folders = [importTarget];
            folders.map((x) => {
                const newFolderName = `${importTarget.name}/${x.name}`;
                const f = new bw_FolderView();
                f.name = newFolderName;
                importResult.folders.push(f);
            });
            const relationships = [...importResult.folderRelationships];
            importResult.folderRelationships = [...noFolderRelationShips];
            relationships.map((x) => {
                importResult.folderRelationships.push([x[0], x[1] + 1]);
            });
        });
    }
}

;// ../../libs/importer/src/services/index.ts






;// ../../libs/importer/src/index.ts



;// external "crypto"
const bw_external_crypto_namespaceObject = require("crypto");
;// external "node-forge"
const bw_external_node_forge_namespaceObject = require("node-forge");
;// ../../libs/node/src/services/node-crypto-function.service.ts
var bw_node_crypto_function_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};



class bw_NodeCryptoFunctionService {
    pbkdf2(password, salt, algorithm, iterations) {
        const len = algorithm === "sha256" ? 32 : 64;
        const nodePassword = this.toNodeValue(password);
        const nodeSalt = this.toNodeValue(salt);
        return new Promise((resolve, reject) => {
            bw_external_crypto_namespaceObject.pbkdf2(nodePassword, nodeSalt, iterations, len, algorithm, (error, key) => {
                if (error != null) {
                    reject(error);
                }
                else {
                    resolve(this.toUint8Buffer(key));
                }
            });
        });
    }
    argon2(password, salt, iterations, memory, parallelism) {
        return bw_node_crypto_function_service_awaiter(this, void 0, void 0, function* () {
            const nodePassword = this.toNodeValue(password);
            const nodeSalt = this.toNodeBuffer(this.toUint8Buffer(salt));
            const argon2 = yield Promise.resolve(/* import() */).then(__webpack_require__.t.bind(__webpack_require__, 329, 23));
            const hash = yield argon2.hash(nodePassword, {
                salt: nodeSalt,
                raw: true,
                hashLength: 32,
                timeCost: iterations,
                memoryCost: memory,
                parallelism: parallelism,
                type: argon2.argon2id,
            });
            return this.toUint8Buffer(hash);
        });
    }
    // ref: https://tools.ietf.org/html/rfc5869
    hkdf(ikm, salt, info, outputByteSize, algorithm) {
        return bw_node_crypto_function_service_awaiter(this, void 0, void 0, function* () {
            const saltBuf = this.toUint8Buffer(salt);
            const prk = yield this.hmac(ikm, saltBuf, algorithm);
            return this.hkdfExpand(prk, info, outputByteSize, algorithm);
        });
    }
    // ref: https://tools.ietf.org/html/rfc5869
    hkdfExpand(prk, info, outputByteSize, algorithm) {
        return bw_node_crypto_function_service_awaiter(this, void 0, void 0, function* () {
            const hashLen = algorithm === "sha256" ? 32 : 64;
            if (outputByteSize > 255 * hashLen) {
                throw new Error("outputByteSize is too large.");
            }
            const prkArr = new Uint8Array(prk);
            if (prkArr.length < hashLen) {
                throw new Error("prk is too small.");
            }
            const infoBuf = this.toUint8Buffer(info);
            const infoArr = new Uint8Array(infoBuf);
            let runningOkmLength = 0;
            let previousT = new Uint8Array(0);
            const n = Math.ceil(outputByteSize / hashLen);
            const okm = new Uint8Array(n * hashLen);
            for (let i = 0; i < n; i++) {
                const t = new Uint8Array(previousT.length + infoArr.length + 1);
                t.set(previousT);
                t.set(infoArr, previousT.length);
                t.set([i + 1], t.length - 1);
                previousT = yield this.hmac(t, prk, algorithm);
                okm.set(previousT, runningOkmLength);
                runningOkmLength += previousT.length;
                if (runningOkmLength >= outputByteSize) {
                    break;
                }
            }
            return okm.slice(0, outputByteSize);
        });
    }
    hash(value, algorithm) {
        const nodeValue = this.toNodeValue(value);
        const hash = bw_external_crypto_namespaceObject.createHash(algorithm);
        hash.update(nodeValue);
        return Promise.resolve(this.toUint8Buffer(hash.digest()));
    }
    hmac(value, key, algorithm) {
        const nodeValue = this.toNodeBuffer(value);
        const nodeKey = this.toNodeBuffer(key);
        const hmac = bw_external_crypto_namespaceObject.createHmac(algorithm, nodeKey);
        hmac.update(nodeValue);
        return Promise.resolve(this.toUint8Buffer(hmac.digest()));
    }
    compare(a, b) {
        return bw_node_crypto_function_service_awaiter(this, void 0, void 0, function* () {
            const key = yield this.randomBytes(32);
            const mac1 = yield this.hmac(a, key, "sha256");
            const mac2 = yield this.hmac(b, key, "sha256");
            if (mac1.byteLength !== mac2.byteLength) {
                return false;
            }
            const arr1 = new Uint8Array(mac1);
            const arr2 = new Uint8Array(mac2);
            for (let i = 0; i < arr2.length; i++) {
                if (arr1[i] !== arr2[i]) {
                    return false;
                }
            }
            return true;
        });
    }
    hmacFast(value, key, algorithm) {
        return this.hmac(value, key, algorithm);
    }
    compareFast(a, b) {
        return this.compare(a, b);
    }
    aesEncrypt(data, iv, key) {
        const nodeData = this.toNodeBuffer(data);
        const nodeIv = this.toNodeBuffer(iv);
        const nodeKey = this.toNodeBuffer(key);
        const cipher = bw_external_crypto_namespaceObject.createCipheriv("aes-256-cbc", nodeKey, nodeIv);
        const encBuf = Buffer.concat([cipher.update(nodeData), cipher.final()]);
        return Promise.resolve(this.toUint8Buffer(encBuf));
    }
    aesDecryptFastParameters(data, iv, mac, key) {
        const p = {};
        p.encKey = key.encKey;
        p.data = bw_utils_Utils.fromB64ToArray(data);
        p.iv = bw_utils_Utils.fromB64ToArray(iv);
        const macData = new Uint8Array(p.iv.byteLength + p.data.byteLength);
        macData.set(new Uint8Array(p.iv), 0);
        macData.set(new Uint8Array(p.data), p.iv.byteLength);
        p.macData = macData;
        if (key.macKey != null) {
            p.macKey = key.macKey;
        }
        if (mac != null) {
            p.mac = bw_utils_Utils.fromB64ToArray(mac);
        }
        return p;
    }
    aesDecryptFast(_a) {
        return bw_node_crypto_function_service_awaiter(this, arguments, void 0, function* ({ mode, parameters, }) {
            const iv = mode === "cbc" ? parameters.iv : null;
            const decBuf = yield this.aesDecrypt(parameters.data, iv, parameters.encKey, mode);
            return bw_utils_Utils.fromBufferToUtf8(decBuf);
        });
    }
    aesDecrypt(data, iv, key, mode) {
        const nodeData = this.toNodeBuffer(data);
        const nodeIv = this.toNodeBufferOrNull(iv);
        const nodeKey = this.toNodeBuffer(key);
        const decipher = bw_external_crypto_namespaceObject.createDecipheriv(this.toNodeCryptoAesMode(mode), nodeKey, nodeIv);
        const decBuf = Buffer.concat([decipher.update(nodeData), decipher.final()]);
        return Promise.resolve(this.toUint8Buffer(decBuf));
    }
    rsaEncrypt(data, publicKey, algorithm) {
        if (algorithm === "sha256") {
            throw new Error("Node crypto does not support RSA-OAEP SHA-256");
        }
        const pem = this.toPemPublicKey(publicKey);
        const decipher = bw_external_crypto_namespaceObject.publicEncrypt(pem, this.toNodeBuffer(data));
        return Promise.resolve(this.toUint8Buffer(decipher));
    }
    rsaDecrypt(data, privateKey, algorithm) {
        if (algorithm === "sha256") {
            throw new Error("Node crypto does not support RSA-OAEP SHA-256");
        }
        const pem = this.toPemPrivateKey(privateKey);
        const decipher = bw_external_crypto_namespaceObject.privateDecrypt(pem, this.toNodeBuffer(data));
        return Promise.resolve(this.toUint8Buffer(decipher));
    }
    rsaExtractPublicKey(privateKey) {
        const privateKeyByteString = bw_utils_Utils.fromBufferToByteString(privateKey);
        const privateKeyAsn1 = bw_external_node_forge_namespaceObject.asn1.fromDer(privateKeyByteString);
        const forgePrivateKey = bw_external_node_forge_namespaceObject.pki.privateKeyFromAsn1(privateKeyAsn1);
        const forgePublicKey = bw_external_node_forge_namespaceObject.pki.setRsaPublicKey(forgePrivateKey.n, forgePrivateKey.e);
        const publicKeyAsn1 = bw_external_node_forge_namespaceObject.pki.publicKeyToAsn1(forgePublicKey);
        const publicKeyByteString = bw_external_node_forge_namespaceObject.asn1.toDer(publicKeyAsn1).data;
        const publicKeyArray = bw_utils_Utils.fromByteStringToArray(publicKeyByteString);
        return Promise.resolve(publicKeyArray);
    }
    rsaGenerateKeyPair(length) {
        return bw_node_crypto_function_service_awaiter(this, void 0, void 0, function* () {
            return new Promise((resolve, reject) => {
                bw_external_node_forge_namespaceObject.pki.rsa.generateKeyPair({
                    bits: length,
                    workers: -1,
                    e: 0x10001, // 65537
                }, (error, keyPair) => {
                    if (error != null) {
                        reject(error);
                        return;
                    }
                    const publicKeyAsn1 = bw_external_node_forge_namespaceObject.pki.publicKeyToAsn1(keyPair.publicKey);
                    const publicKeyByteString = bw_external_node_forge_namespaceObject.asn1.toDer(publicKeyAsn1).getBytes();
                    const publicKey = bw_utils_Utils.fromByteStringToArray(publicKeyByteString);
                    const privateKeyAsn1 = bw_external_node_forge_namespaceObject.pki.privateKeyToAsn1(keyPair.privateKey);
                    const privateKeyPkcs8 = bw_external_node_forge_namespaceObject.pki.wrapRsaPrivateKey(privateKeyAsn1);
                    const privateKeyByteString = bw_external_node_forge_namespaceObject.asn1.toDer(privateKeyPkcs8).getBytes();
                    const privateKey = bw_utils_Utils.fromByteStringToArray(privateKeyByteString);
                    resolve([publicKey, privateKey]);
                });
            });
        });
    }
    aesGenerateKey(bitLength) {
        return this.randomBytes(bitLength / 8);
    }
    randomBytes(length) {
        return new Promise((resolve, reject) => {
            bw_external_crypto_namespaceObject.randomBytes(length, (error, bytes) => {
                if (error != null) {
                    reject(error);
                }
                else {
                    resolve(this.toUint8Buffer(bytes));
                }
            });
        });
    }
    toNodeValue(value) {
        let nodeValue;
        if (typeof value === "string") {
            nodeValue = value;
        }
        else {
            nodeValue = this.toNodeBuffer(value);
        }
        return nodeValue;
    }
    toNodeBuffer(value) {
        return Buffer.from(value);
    }
    toNodeBufferOrNull(value) {
        if (value == null) {
            return null;
        }
        return this.toNodeBuffer(value);
    }
    toUint8Buffer(value) {
        let buf;
        if (typeof value === "string") {
            buf = bw_utils_Utils.fromUtf8ToArray(value);
        }
        else {
            buf = value;
        }
        return buf;
    }
    toPemPrivateKey(key) {
        const byteString = bw_utils_Utils.fromBufferToByteString(key);
        const asn1 = bw_external_node_forge_namespaceObject.asn1.fromDer(byteString);
        const privateKey = bw_external_node_forge_namespaceObject.pki.privateKeyFromAsn1(asn1);
        const rsaPrivateKey = bw_external_node_forge_namespaceObject.pki.privateKeyToAsn1(privateKey);
        const privateKeyInfo = bw_external_node_forge_namespaceObject.pki.wrapRsaPrivateKey(rsaPrivateKey);
        return bw_external_node_forge_namespaceObject.pki.privateKeyInfoToPem(privateKeyInfo);
    }
    toPemPublicKey(key) {
        const byteString = bw_utils_Utils.fromBufferToByteString(key);
        const asn1 = bw_external_node_forge_namespaceObject.asn1.fromDer(byteString);
        const publicKey = bw_external_node_forge_namespaceObject.pki.publicKeyFromAsn1(asn1);
        return bw_external_node_forge_namespaceObject.pki.publicKeyToPem(publicKey);
    }
    toNodeCryptoAesMode(mode) {
        return mode === "cbc" ? "aes-256-cbc" : "aes-256-ecb";
    }
}

;// ./src/key-management/cli-biometrics-service.ts
var bw_cli_biometrics_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};

class bw_CliBiometricsService extends bw_BiometricsService {
    authenticateWithBiometrics() {
        return bw_cli_biometrics_service_awaiter(this, void 0, void 0, function* () {
            return false;
        });
    }
    getBiometricsStatus() {
        return bw_cli_biometrics_service_awaiter(this, void 0, void 0, function* () {
            return bw_BiometricsStatus.PlatformUnsupported;
        });
    }
    unlockWithBiometricsForUser(userId) {
        return bw_cli_biometrics_service_awaiter(this, void 0, void 0, function* () {
            return null;
        });
    }
    getBiometricsStatusForUser(userId) {
        return bw_cli_biometrics_service_awaiter(this, void 0, void 0, function* () {
            return bw_BiometricsStatus.PlatformUnsupported;
        });
    }
    getShouldAutopromptNow() {
        return bw_cli_biometrics_service_awaiter(this, void 0, void 0, function* () {
            return false;
        });
    }
    setShouldAutopromptNow(value) {
        return bw_cli_biometrics_service_awaiter(this, void 0, void 0, function* () { });
    }
}

;// ./src/platform/flags.ts

function bw_flags_flagEnabled(flag) {
    return bw_flagEnabled(flag);
}
function bw_flags_devFlagEnabled(flag) {
    return baseDevFlagEnabled(flag);
}
function bw_flags_devFlagValue(flag) {
    return baseDevFlagValue(flag);
}

;// external "child_process"
const bw_external_child_process_namespaceObject = require("child_process");
;// ./src/platform/services/cli-platform-utils.service.ts
var bw_cli_platform_utils_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


// eslint-disable-next-line
const bw_cli_platform_utils_service_open = __webpack_require__(80);
class bw_CliPlatformUtilsService {
    constructor(clientType, packageJson) {
        this.packageJson = packageJson;
        this.deviceCache = null;
        this.clientType = clientType;
    }
    getDevice() {
        if (!this.deviceCache) {
            switch (process.platform) {
                case "win32":
                    this.deviceCache = bw_DeviceType.WindowsCLI;
                    break;
                case "darwin":
                    this.deviceCache = bw_DeviceType.MacOsCLI;
                    break;
                case "linux":
                default:
                    this.deviceCache = bw_DeviceType.LinuxCLI;
                    break;
            }
        }
        return this.deviceCache;
    }
    getDeviceString() {
        const device = bw_DeviceType[this.getDevice()].toLowerCase();
        return device.replace("cli", "");
    }
    getClientType() {
        return this.clientType;
    }
    isFirefox() {
        return false;
    }
    isChrome() {
        return false;
    }
    isEdge() {
        return false;
    }
    isOpera() {
        return false;
    }
    isVivaldi() {
        return false;
    }
    isSafari() {
        return false;
    }
    isMacAppStore() {
        return false;
    }
    isViewOpen() {
        return Promise.resolve(false);
    }
    launchUri(uri, options) {
        if (process.platform === "linux") {
            bw_external_child_process_namespaceObject.spawnSync("xdg-open", [uri]);
        }
        else {
            bw_cli_platform_utils_service_open(uri);
        }
    }
    getApplicationVersion() {
        return Promise.resolve(this.packageJson.version);
    }
    getApplicationVersionNumber() {
        return bw_cli_platform_utils_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.getApplicationVersion()).split(RegExp("[+|-]"))[0].trim();
        });
    }
    getApplicationVersionSync() {
        return this.packageJson.version;
    }
    supportsWebAuthn(win) {
        return false;
    }
    supportsDuo() {
        return false;
    }
    showToast(type, title, text, options) {
        throw new Error("Not implemented.");
    }
    isDev() {
        return "production" === "development";
    }
    isSelfHost() {
        return false;
    }
    copyToClipboard(text, options) {
        throw new Error("Not implemented.");
    }
    readFromClipboard(options) {
        throw new Error("Not implemented.");
    }
    supportsSecureStorage() {
        return false;
    }
    getAutofillKeyboardShortcut() {
        return null;
    }
}

;// ../../node_modules/@bitwarden/sdk-internal/index.js


// In order to support a fallback strategy for web we need to conditionally load the wasm file
function bw_init(wasm) {
  (0,bw_bitwarden_wasm_internal_bg/* __wbg_set_wasm */.lI)(wasm);
}



;// ./src/platform/services/cli-sdk-load.service.ts
var bw_cli_sdk_load_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};


class bw_CliSdkLoadService extends bw_SdkLoadService {
    load() {
        return bw_cli_sdk_load_service_awaiter(this, void 0, void 0, function* () {
            const module = yield __webpack_require__.e(/* import() */ 502).then(__webpack_require__.bind(__webpack_require__, 502));
            bw_init(module);
        });
    }
}

;// ./src/platform/services/console-log.service.ts

class bw_ConsoleLogService extends bw_console_log_service_ConsoleLogService {
    constructor(isDev, filter = null) {
        super(isDev, filter);
    }
    write(level, message, ...optionalParams) {
        if (this.filter != null && this.filter(level)) {
            return;
        }
        if (process.env.BW_RESPONSE === "true") {
            // eslint-disable-next-line
            console.error(message, ...optionalParams);
            return;
        }
        super.write(level, message, ...optionalParams);
    }
}

;// ../../libs/common/src/platform/services/translation.service.ts
var bw_translation_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
class bw_TranslationService {
    constructor(systemLanguage, localesDirectory, getLocalesJson) {
        this.systemLanguage = systemLanguage;
        this.localesDirectory = localesDirectory;
        this.getLocalesJson = getLocalesJson;
        // First locale is the default (English)
        this.supportedTranslationLocales = ["en"];
        this.defaultLocale = "en";
        this.localeNames = new Map([
            ["af", "Afrikaans"],
            ["ar", "العربية الفصحى"],
            ["az", "Azərbaycanca"],
            ["be", "Беларуская"],
            ["bg", "български"],
            ["bn", "বাংলা"],
            ["bs", "bosanski jezik"],
            ["ca", "català"],
            ["cs", "čeština"],
            ["cy", "Cymraeg, y Gymraeg"],
            ["da", "dansk"],
            ["de", "Deutsch"],
            ["el", "Ελληνικά"],
            ["en", "English"],
            ["en-GB", "English (British)"],
            ["en-IN", "English (India)"],
            ["eo", "Esperanto"],
            ["es", "español"],
            ["et", "eesti"],
            ["eu", "euskara"],
            ["fa", "فارسی"],
            ["fi", "suomi"],
            ["fil", "Wikang Filipino"],
            ["fr", "français"],
            ["gl", "galego"],
            ["he", "עברית"],
            ["hi", "हिन्दी"],
            ["hr", "hrvatski"],
            ["hu", "magyar"],
            ["id", "Bahasa Indonesia"],
            ["it", "italiano"],
            ["ja", "日本語"],
            ["ka", "ქართული"],
            ["km", "ខ្មែរ, ខេមរភាសា, ភាសាខ្មែរ"],
            ["kn", "ಕನ್ನಡ"],
            ["ko", "한국어"],
            ["lt", "lietuvių kalba"],
            ["lv", "Latvietis"],
            ["me", "црногорски"],
            ["ml", "മലയാളം"],
            ["mr", "मराठी"],
            ["my", "ဗမာစကား"],
            ["nb", "norsk (bokmål)"],
            ["ne", "नेपाली"],
            ["nl", "Nederlands"],
            ["nn", "Norsk Nynorsk"],
            ["or", "ଓଡ଼ିଆ"],
            ["pl", "polski"],
            ["pt-BR", "português do Brasil"],
            ["pt-PT", "português"],
            ["ro", "română"],
            ["ru", "русский"],
            ["si", "සිංහල"],
            ["sk", "slovenčina"],
            ["sl", "Slovenski jezik, Slovenščina"],
            ["sr", "Српски"],
            ["sv", "svenska"],
            ["te", "తెలుగు"],
            ["th", "ไทย"],
            ["tr", "Türkçe"],
            ["uk", "українська"],
            ["vi", "Tiếng Việt"],
            ["zh-CN", "中文（中国大陆）"],
            ["zh-TW", "中文（台灣）"],
        ]);
        this.defaultMessages = {};
        this.localeMessages = {};
        this.systemLanguage = systemLanguage.replace("_", "-");
    }
    init(locale) {
        return bw_translation_service_awaiter(this, void 0, void 0, function* () {
            if (this.inited) {
                throw new Error("i18n already initialized.");
            }
            if (this.supportedTranslationLocales == null || this.supportedTranslationLocales.length === 0) {
                throw new Error("supportedTranslationLocales not set.");
            }
            this.inited = true;
            this.translationLocale = locale != null ? locale : this.systemLanguage;
            try {
                this.collator = new Intl.Collator(this.translationLocale, {
                    numeric: true,
                    sensitivity: "base",
                });
            }
            catch (_a) {
                this.collator = null;
            }
            if (this.supportedTranslationLocales.indexOf(this.translationLocale) === -1) {
                this.translationLocale = this.translationLocale.slice(0, 2);
                if (this.supportedTranslationLocales.indexOf(this.translationLocale) === -1) {
                    this.translationLocale = this.defaultLocale;
                }
            }
            if (this.localesDirectory != null) {
                yield this.loadMessages(this.translationLocale, this.localeMessages);
                if (this.translationLocale !== this.defaultLocale) {
                    yield this.loadMessages(this.defaultLocale, this.defaultMessages);
                }
            }
        });
    }
    t(id, p1, p2, p3) {
        return this.translate(id, p1, p2, p3);
    }
    translate(id, p1, p2, p3) {
        let result;
        // eslint-disable-next-line
        if (this.localeMessages.hasOwnProperty(id) && this.localeMessages[id]) {
            result = this.localeMessages[id];
            // eslint-disable-next-line
        }
        else if (this.defaultMessages.hasOwnProperty(id) && this.defaultMessages[id]) {
            result = this.defaultMessages[id];
        }
        else {
            result = "";
        }
        if (result !== "") {
            if (p1 != null) {
                result = result.split("__$1__").join(p1.toString());
            }
            if (p2 != null) {
                result = result.split("__$2__").join(p2.toString());
            }
            if (p3 != null) {
                result = result.split("__$3__").join(p3.toString());
            }
        }
        return result;
    }
    loadMessages(locale, messagesObj) {
        return bw_translation_service_awaiter(this, void 0, void 0, function* () {
            const formattedLocale = locale.replace("-", "_");
            const locales = yield this.getLocalesJson(formattedLocale);
            for (const prop in locales) {
                // eslint-disable-next-line
                if (!locales.hasOwnProperty(prop)) {
                    continue;
                }
                messagesObj[prop] = locales[prop].message;
                if (locales[prop].placeholders) {
                    for (const placeProp in locales[prop].placeholders) {
                        if (!locales[prop].placeholders.hasOwnProperty(placeProp) || // eslint-disable-line
                            !locales[prop].placeholders[placeProp].content) {
                            continue;
                        }
                        const replaceToken = "\\$" + placeProp.toUpperCase() + "\\$";
                        let replaceContent = locales[prop].placeholders[placeProp].content;
                        if (replaceContent === "$1" || replaceContent === "$2" || replaceContent === "$3") {
                            replaceContent = "__$" + replaceContent + "__";
                        }
                        messagesObj[prop] = messagesObj[prop].replace(new RegExp(replaceToken, "g"), replaceContent);
                    }
                }
            }
        });
    }
}

;// ../../libs/common/src/platform/services/i18n.service.ts
var bw_i18n_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



const bw_i18n_service_LOCALE_KEY = new bw_KeyDefinition(bw_TRANSLATION_DISK, "locale", {
    deserializer: (value) => value,
});
class bw_i18n_service_I18nService extends bw_TranslationService {
    constructor(systemLanguage, localesDirectory, getLocalesJson, globalStateProvider) {
        super(systemLanguage, localesDirectory, getLocalesJson);
        this.systemLanguage = systemLanguage;
        this.localesDirectory = localesDirectory;
        this.getLocalesJson = getLocalesJson;
        this.translationLocaleState = globalStateProvider.get(bw_i18n_service_LOCALE_KEY);
        this.userSetLocale$ = this.translationLocaleState.state$;
        this.locale$ = this.userSetLocale$.pipe((0,bw_external_rxjs_namespaceObject.map)((locale) => locale !== null && locale !== void 0 ? locale : this.translationLocale));
    }
    setLocale(locale) {
        return bw_i18n_service_awaiter(this, void 0, void 0, function* () {
            yield this.translationLocaleState.update(() => locale);
        });
    }
    init() {
        const _super = Object.create(null, {
            init: { get: () => super.init }
        });
        return bw_i18n_service_awaiter(this, void 0, void 0, function* () {
            const storedLocale = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.translationLocaleState.state$);
            yield _super.init.call(this, storedLocale);
        });
    }
}

;// ./src/platform/services/i18n.service.ts



class bw_I18nService extends bw_i18n_service_I18nService {
    constructor(systemLanguage, localesDirectory, globalStateProvider) {
        super(systemLanguage, localesDirectory, (formattedLocale) => {
            const filePath = bw_external_path_namespaceObject.join(__dirname, this.localesDirectory + "/" + formattedLocale + "/messages.json");
            const localesJson = bw_external_fs_namespaceObject.readFileSync(filePath, "utf8");
            const locales = JSON.parse(localesJson.replace(/^\uFEFF/, "")); // strip the BOM
            return Promise.resolve(locales);
        }, globalStateProvider);
        this.supportedTranslationLocales = ["en"];
    }
}

;// external "lowdb"
const bw_external_lowdb_namespaceObject = require("lowdb");
;// external "lowdb/adapters/FileSync"
const bw_FileSync_namespaceObject = require("lowdb/adapters/FileSync");
;// external "proper-lockfile"
const bw_external_proper_lockfile_namespaceObject = require("proper-lockfile");
;// ./src/platform/services/lowdb-storage.service.ts
var bw_lowdb_storage_service_decorate = (undefined && undefined.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
var bw_lowdb_storage_service_metadata = (undefined && undefined.__metadata) || function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
};
var bw_lowdb_storage_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore









const bw_retries = {
    retries: 50,
    minTimeout: 100,
    maxTimeout: 250,
    factor: 2,
};
class bw_LowdbStorageService {
    constructor(logService, defaults, dir, allowCache = false, requireLock = false) {
        this.logService = logService;
        this.dir = dir;
        this.allowCache = allowCache;
        this.requireLock = requireLock;
        this.ready = false;
        this.updatesSubject = new bw_external_rxjs_namespaceObject.Subject();
        this.defaults = defaults;
        this.updates$ = this.updatesSubject.asObservable();
    }
    init() {
        return bw_lowdb_storage_service_awaiter(this, void 0, void 0, function* () {
            if (this.ready) {
                return;
            }
            this.logService.info("Initializing lowdb storage service.");
            let adapter;
            if (bw_utils_Utils.isNode && this.dir != null) {
                if (!bw_external_fs_namespaceObject.existsSync(this.dir)) {
                    this.logService.warning(`Could not find dir, "${this.dir}"; creating it instead.`);
                    bw_NodeUtils.mkdirpSync(this.dir, "700");
                    this.logService.info(`Created dir "${this.dir}".`);
                }
                this.dataFilePath = bw_external_path_namespaceObject.join(this.dir, "data.json");
                if (!bw_external_fs_namespaceObject.existsSync(this.dataFilePath)) {
                    this.logService.warning(`Could not find data file, "${this.dataFilePath}"; creating it instead.`);
                    bw_external_fs_namespaceObject.writeFileSync(this.dataFilePath, "", { mode: 0o600 });
                    bw_external_fs_namespaceObject.chmodSync(this.dataFilePath, 0o600);
                    this.logService.info(`Created data file "${this.dataFilePath}" with chmod 600.`);
                }
                else {
                    this.logService.info(`db file "${this.dataFilePath} already exists"; using existing db`);
                }
                yield this.lockDbFile(() => {
                    adapter = new bw_FileSync_namespaceObject(this.dataFilePath);
                });
            }
            try {
                this.logService.info("Attempting to create lowdb storage adapter.");
                this.db = bw_external_lowdb_namespaceObject(adapter);
                this.logService.info("Successfully created lowdb storage adapter.");
            }
            catch (e) {
                if (e instanceof SyntaxError) {
                    this.logService.warning(`Error creating lowdb storage adapter, "${e.message}"; emptying data file.`);
                    if (bw_external_fs_namespaceObject.existsSync(this.dataFilePath)) {
                        const backupPath = this.dataFilePath + ".bak";
                        this.logService.warning(`Writing backup of data file to ${backupPath}`);
                        yield bw_external_fs_namespaceObject.copyFile(this.dataFilePath, backupPath, () => {
                            this.logService.warning(`Error while creating data file backup, "${e.message}". No backup may have been created.`);
                        });
                    }
                    adapter.write({});
                    this.db = bw_external_lowdb_namespaceObject(adapter);
                }
                else {
                    this.logService.error(`Error creating lowdb storage adapter, "${e.message}".`);
                    throw e;
                }
            }
            if (this.defaults != null) {
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.lockDbFile(() => {
                    this.logService.info("Writing defaults.");
                    this.readForNoCache();
                    this.db.defaults(this.defaults).write();
                    this.logService.info("Successfully wrote defaults to db.");
                });
            }
            this.ready = true;
        });
    }
    get valuesRequireDeserialization() {
        return true;
    }
    get(key) {
        return bw_lowdb_storage_service_awaiter(this, void 0, void 0, function* () {
            yield this.waitForReady();
            return this.lockDbFile(() => {
                this.readForNoCache();
                const val = this.db.get(key).value();
                this.logService.debug(`Successfully read ${key} from db`);
                if (val == null) {
                    return null;
                }
                return val;
            });
        });
    }
    has(key) {
        return this.get(key).then((v) => v != null);
    }
    save(key, obj) {
        return bw_lowdb_storage_service_awaiter(this, void 0, void 0, function* () {
            yield this.waitForReady();
            return this.lockDbFile(() => {
                this.readForNoCache();
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.db.set(key, obj).write();
                this.updatesSubject.next({ key, updateType: "save" });
                this.logService.debug(`Successfully wrote ${key} to db`);
                return;
            });
        });
    }
    remove(key) {
        return bw_lowdb_storage_service_awaiter(this, void 0, void 0, function* () {
            yield this.waitForReady();
            return this.lockDbFile(() => {
                this.readForNoCache();
                // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                // eslint-disable-next-line @typescript-eslint/no-floating-promises
                this.db.unset(key).write();
                this.updatesSubject.next({ key, updateType: "remove" });
                this.logService.debug(`Successfully removed ${key} from db`);
                return;
            });
        });
    }
    lockDbFile(action) {
        return bw_lowdb_storage_service_awaiter(this, void 0, void 0, function* () {
            if (this.requireLock && !bw_utils_Utils.isNullOrWhitespace(this.dataFilePath)) {
                this.logService.info("acquiring db file lock");
                return yield bw_external_proper_lockfile_namespaceObject.lock(this.dataFilePath, { retries: bw_retries }).then((release) => {
                    try {
                        return action();
                    }
                    finally {
                        // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling.
                        // eslint-disable-next-line @typescript-eslint/no-floating-promises
                        release();
                    }
                });
            }
            else {
                return action();
            }
        });
    }
    readForNoCache() {
        if (!this.allowCache) {
            this.db.read();
        }
    }
    waitForReady() {
        return bw_lowdb_storage_service_awaiter(this, void 0, void 0, function* () {
            if (!this.ready) {
                yield this.init();
            }
        });
    }
}
bw_lowdb_storage_service_decorate([
    bw_sequentialize(() => "lowdbStorageInit"),
    bw_lowdb_storage_service_metadata("design:type", Function),
    bw_lowdb_storage_service_metadata("design:paramtypes", []),
    bw_lowdb_storage_service_metadata("design:returntype", Promise)
], bw_LowdbStorageService.prototype, "init", null);

;// external "form-data"
const bw_external_form_data_namespaceObject = require("form-data");
;// external "https-proxy-agent"
const bw_external_https_proxy_agent_namespaceObject = require("https-proxy-agent");
;// external "node-fetch"
const bw_external_node_fetch_namespaceObject = require("node-fetch");
var bw_external_node_fetch_default = /*#__PURE__*/__webpack_require__.n(bw_external_node_fetch_namespaceObject);
;// ../../libs/common/src/admin-console/models/request/collection-bulk-delete.request.ts
class bw_CollectionBulkDeleteRequest {
    constructor(ids) {
        this.ids = ids == null ? [] : ids;
    }
}

;// ../../libs/common/src/admin-console/models/response/organization-connection.response.ts

class bw_OrganizationConnectionResponse extends bw_BaseResponse {
    constructor(response, configType) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.type = this.getResponseProperty("Type");
        this.organizationId = this.getResponseProperty("OrganizationId");
        this.enabled = this.getResponseProperty("Enabled");
        const rawConfig = this.getResponseProperty("Config");
        this.config = rawConfig == null ? null : new configType(rawConfig);
    }
}

;// ../../libs/common/src/vault/models/response/attachment.response.ts

class bw_attachment_response_AttachmentResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.url = this.getResponseProperty("Url");
        this.fileName = this.getResponseProperty("FileName");
        this.key = this.getResponseProperty("Key");
        this.size = this.getResponseProperty("Size");
        this.sizeName = this.getResponseProperty("SizeName");
    }
}

;// ../../libs/common/src/vault/models/response/password-history.response.ts

class bw_password_history_response_PasswordHistoryResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.password = this.getResponseProperty("Password");
        this.lastUsedDate = this.getResponseProperty("LastUsedDate");
    }
}

;// ../../libs/common/src/vault/models/response/cipher.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore











class bw_cipher_response_CipherResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.organizationId = this.getResponseProperty("OrganizationId");
        this.folderId = this.getResponseProperty("FolderId") || null;
        this.type = this.getResponseProperty("Type");
        this.name = this.getResponseProperty("Name");
        this.notes = this.getResponseProperty("Notes");
        this.favorite = this.getResponseProperty("Favorite") || false;
        this.edit = !!this.getResponseProperty("Edit");
        if (this.getResponseProperty("ViewPassword") == null) {
            this.viewPassword = true;
        }
        else {
            this.viewPassword = this.getResponseProperty("ViewPassword");
        }
        this.permissions = new bw_CipherPermissionsApi(this.getResponseProperty("Permissions"));
        this.organizationUseTotp = this.getResponseProperty("OrganizationUseTotp");
        this.revisionDate = this.getResponseProperty("RevisionDate");
        this.collectionIds = this.getResponseProperty("CollectionIds");
        this.creationDate = this.getResponseProperty("CreationDate");
        this.deletedDate = this.getResponseProperty("DeletedDate");
        const login = this.getResponseProperty("Login");
        if (login != null) {
            this.login = new bw_LoginApi(login);
        }
        const card = this.getResponseProperty("Card");
        if (card != null) {
            this.card = new bw_CardApi(card);
        }
        const identity = this.getResponseProperty("Identity");
        if (identity != null) {
            this.identity = new bw_IdentityApi(identity);
        }
        const secureNote = this.getResponseProperty("SecureNote");
        if (secureNote != null) {
            this.secureNote = new bw_SecureNoteApi(secureNote);
        }
        const sshKey = this.getResponseProperty("sshKey");
        if (sshKey != null) {
            this.sshKey = new bw_SshKeyApi(sshKey);
        }
        const fields = this.getResponseProperty("Fields");
        if (fields != null) {
            this.fields = fields.map((f) => new bw_FieldApi(f));
        }
        const attachments = this.getResponseProperty("Attachments");
        if (attachments != null) {
            this.attachments = attachments.map((a) => new bw_attachment_response_AttachmentResponse(a));
        }
        const passwordHistory = this.getResponseProperty("PasswordHistory");
        if (passwordHistory != null) {
            this.passwordHistory = passwordHistory.map((h) => new bw_password_history_response_PasswordHistoryResponse(h));
        }
        this.reprompt = this.getResponseProperty("Reprompt") || bw_CipherRepromptType.None;
        this.key = this.getResponseProperty("Key") || null;
    }
}

;// ../../libs/common/src/admin-console/models/response/organization-export.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore



class bw_OrganizationExportResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        const collections = this.getResponseProperty("Collections");
        if (collections != null) {
            this.collections = collections.map((c) => new bw_CollectionResponse(c));
        }
        const ciphers = this.getResponseProperty("Ciphers");
        if (ciphers != null) {
            this.ciphers = ciphers.map((c) => new bw_cipher_response_CipherResponse(c));
        }
    }
}

;// ../../libs/common/src/admin-console/models/response/organization-sponsorship-sync-status.response.ts

class bw_OrganizationSponsorshipSyncStatusResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        const lastSyncDate = this.getResponseProperty("LastSyncDate");
        if (lastSyncDate) {
            this.lastSyncDate = new Date(lastSyncDate);
        }
    }
}

;// ../../libs/common/src/admin-console/models/response/pre-validate-sponsorship.response.ts

class bw_PreValidateSponsorshipResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.isTokenValid = this.getResponseProperty("IsTokenValid");
        this.isFreeFamilyPolicyEnabled = this.getResponseProperty("IsFreeFamilyPolicyEnabled");
    }
}

;// ../../libs/common/src/admin-console/models/response/provider/provider-organization.response.ts

class bw_ProviderOrganizationResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.providerId = this.getResponseProperty("ProviderId");
        this.organizationId = this.getResponseProperty("OrganizationId");
        this.key = this.getResponseProperty("Key");
        this.settings = this.getResponseProperty("Settings");
        this.creationDate = this.getResponseProperty("CreationDate");
        this.revisionDate = this.getResponseProperty("RevisionDate");
        this.userCount = this.getResponseProperty("UserCount");
        this.seats = this.getResponseProperty("Seats");
        this.occupiedSeats = this.getResponseProperty("OccupiedSeats");
        this.remainingSeats = this.getResponseProperty("RemainingSeats");
        this.plan = this.getResponseProperty("Plan");
    }
}
class bw_ProviderOrganizationOrganizationDetailsResponse extends bw_ProviderOrganizationResponse {
    constructor(response) {
        super(response);
        this.organizationName = this.getResponseProperty("OrganizationName");
    }
}

;// ../../libs/common/src/admin-console/models/response/provider/provider-user-bulk-public-key.response.ts

class bw_ProviderUserBulkPublicKeyResponse extends bw_OrganizationUserBulkPublicKeyResponse {
}

;// ../../libs/common/src/admin-console/models/response/provider/provider-user-bulk.response.ts

class bw_ProviderUserBulkResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.error = this.getResponseProperty("Error");
    }
}

;// ../../libs/common/src/admin-console/models/response/provider/provider-user.response.ts


class bw_ProviderUserResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.id = this.getResponseProperty("Id");
        this.userId = this.getResponseProperty("UserId");
        this.type = this.getResponseProperty("Type");
        this.status = this.getResponseProperty("Status");
        this.permissions = new bw_PermissionsApi(this.getResponseProperty("Permissions"));
    }
}
class bw_ProviderUserUserDetailsResponse extends bw_ProviderUserResponse {
    constructor(response) {
        super(response);
        this.name = this.getResponseProperty("Name");
        this.email = this.getResponseProperty("Email");
    }
}

;// ../../libs/common/src/auth/models/response/device-verification.response.ts

class bw_DeviceVerificationResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.isDeviceVerificationSectionEnabled = this.getResponseProperty("IsDeviceVerificationSectionEnabled");
        this.unknownDeviceVerificationEnabled = this.getResponseProperty("UnknownDeviceVerificationEnabled");
    }
}

;// ../../libs/common/src/auth/models/response/key-connector-user-key.response.ts

class bw_KeyConnectorUserKeyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.key = this.getResponseProperty("Key");
    }
}

;// ../../libs/common/src/auth/models/response/prelogin.response.ts

class bw_PreloginResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.kdf = this.getResponseProperty("Kdf");
        this.kdfIterations = this.getResponseProperty("KdfIterations");
        this.kdfMemory = this.getResponseProperty("KdfMemory");
        this.kdfParallelism = this.getResponseProperty("KdfParallelism");
    }
}

;// ../../libs/common/src/auth/models/response/register.response.ts

class bw_RegisterResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.captchaBypassToken = this.getResponseProperty("CaptchaBypassToken");
    }
}

;// ../../libs/common/src/auth/models/response/sso-pre-validate.response.ts

class bw_SsoPreValidateResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.token = this.getResponseProperty("Token");
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-authenticator.response.ts

class bw_TwoFactorAuthenticatorResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        this.key = this.getResponseProperty("Key");
        this.userVerificationToken = this.getResponseProperty("UserVerificationToken");
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-duo.response.ts

class bw_TwoFactorDuoResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        this.host = this.getResponseProperty("Host");
        this.clientSecret = this.getResponseProperty("ClientSecret");
        this.clientId = this.getResponseProperty("ClientId");
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-email.response.ts

class bw_TwoFactorEmailResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        this.email = this.getResponseProperty("Email");
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-provider.response.ts

class bw_TwoFactorProviderResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        this.type = this.getResponseProperty("Type");
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-recover.response.ts

class bw_TwoFactorRecoverResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.code = this.getResponseProperty("Code");
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-web-authn.response.ts


class bw_TwoFactorWebAuthnResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        const keys = this.getResponseProperty("Keys");
        this.keys = keys == null ? null : keys.map((k) => new bw_KeyResponse(k));
    }
}
class bw_KeyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.name = this.getResponseProperty("Name");
        this.id = this.getResponseProperty("Id");
        this.migrated = this.getResponseProperty("Migrated");
    }
}
class bw_ChallengeResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.attestation = this.getResponseProperty("attestation");
        this.authenticatorSelection = this.getResponseProperty("authenticatorSelection");
        this.challenge = bw_utils_Utils.fromUrlB64ToArray(this.getResponseProperty("challenge"));
        this.excludeCredentials = this.getResponseProperty("excludeCredentials").map((c) => {
            c.id = bw_utils_Utils.fromUrlB64ToArray(c.id).buffer;
            return c;
        });
        this.extensions = this.getResponseProperty("extensions");
        this.pubKeyCredParams = this.getResponseProperty("pubKeyCredParams");
        this.rp = this.getResponseProperty("rp");
        this.timeout = this.getResponseProperty("timeout");
        const user = this.getResponseProperty("user");
        user.id = bw_utils_Utils.fromUrlB64ToArray(user.id);
        this.user = user;
    }
}

;// ../../libs/common/src/auth/models/response/two-factor-yubi-key.response.ts

class bw_TwoFactorYubiKeyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.enabled = this.getResponseProperty("Enabled");
        this.key1 = this.getResponseProperty("Key1");
        this.key2 = this.getResponseProperty("Key2");
        this.key3 = this.getResponseProperty("Key3");
        this.key4 = this.getResponseProperty("Key4");
        this.key5 = this.getResponseProperty("Key5");
        this.nfc = this.getResponseProperty("Nfc");
    }
}

;// ../../libs/common/src/billing/models/response/billing-payment.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_BillingPaymentResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.balance = this.getResponseProperty("Balance");
        const paymentSource = this.getResponseProperty("PaymentSource");
        this.paymentSource = paymentSource == null ? null : new bw_BillingSourceResponse(paymentSource);
    }
}

;// ../../libs/common/src/models/response/breach-account.response.ts

class bw_BreachAccountResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.addedDate = this.getResponseProperty("AddedDate");
        this.breachDate = this.getResponseProperty("BreachDate");
        this.dataClasses = this.getResponseProperty("DataClasses");
        this.description = this.getResponseProperty("Description");
        this.domain = this.getResponseProperty("Domain");
        this.isActive = this.getResponseProperty("IsActive");
        this.isVerified = this.getResponseProperty("IsVerified");
        this.logoPath = this.getResponseProperty("LogoPath");
        this.modifiedDate = this.getResponseProperty("ModifiedDate");
        this.name = this.getResponseProperty("Name");
        this.pwnCount = this.getResponseProperty("PwnCount");
        this.title = this.getResponseProperty("Title");
    }
}

;// ../../libs/common/src/models/response/global-domain.response.ts

class bw_GlobalDomainResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.type = this.getResponseProperty("Type");
        this.domains = this.getResponseProperty("Domains");
        this.excluded = this.getResponseProperty("Excluded");
    }
}

;// ../../libs/common/src/models/response/domains.response.ts


class bw_DomainsResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.globalEquivalentDomains = [];
        this.equivalentDomains = this.getResponseProperty("EquivalentDomains");
        const globalEquivalentDomains = this.getResponseProperty("GlobalEquivalentDomains");
        if (globalEquivalentDomains != null) {
            this.globalEquivalentDomains = globalEquivalentDomains.map((d) => new bw_GlobalDomainResponse(d));
        }
        else {
            this.globalEquivalentDomains = [];
        }
    }
}

;// ../../libs/common/src/models/response/event.response.ts

class bw_EventResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.type = this.getResponseProperty("Type");
        this.userId = this.getResponseProperty("UserId");
        this.organizationId = this.getResponseProperty("OrganizationId");
        this.providerId = this.getResponseProperty("ProviderId");
        this.cipherId = this.getResponseProperty("CipherId");
        this.collectionId = this.getResponseProperty("CollectionId");
        this.groupId = this.getResponseProperty("GroupId");
        this.policyId = this.getResponseProperty("PolicyId");
        this.organizationUserId = this.getResponseProperty("OrganizationUserId");
        this.providerUserId = this.getResponseProperty("ProviderUserId");
        this.providerOrganizationId = this.getResponseProperty("ProviderOrganizationId");
        this.actingUserId = this.getResponseProperty("ActingUserId");
        this.date = this.getResponseProperty("Date");
        this.deviceType = this.getResponseProperty("DeviceType");
        this.ipAddress = this.getResponseProperty("IpAddress");
        this.installationId = this.getResponseProperty("InstallationId");
        this.systemUser = this.getResponseProperty("SystemUser");
        this.domainName = this.getResponseProperty("DomainName");
        this.secretId = this.getResponseProperty("SecretId");
        this.serviceAccountId = this.getResponseProperty("ServiceAccountId");
    }
}

;// ../../libs/common/src/models/response/user-key.response.ts

class bw_UserKeyResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.userId = this.getResponseProperty("UserId");
        this.publicKey = this.getResponseProperty("PublicKey");
    }
}

;// ../../libs/common/src/platform/sync/sync.response.ts








class bw_SyncResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.folders = [];
        this.collections = [];
        this.ciphers = [];
        this.policies = [];
        this.sends = [];
        const profile = this.getResponseProperty("Profile");
        if (profile != null) {
            this.profile = new bw_ProfileResponse(profile);
        }
        const folders = this.getResponseProperty("Folders");
        if (folders != null) {
            this.folders = folders.map((f) => new bw_folder_response_FolderResponse(f));
        }
        const collections = this.getResponseProperty("Collections");
        if (collections != null) {
            this.collections = collections.map((c) => new bw_CollectionDetailsResponse(c));
        }
        const ciphers = this.getResponseProperty("Ciphers");
        if (ciphers != null) {
            this.ciphers = ciphers.map((c) => new bw_cipher_response_CipherResponse(c));
        }
        const domains = this.getResponseProperty("Domains");
        if (domains != null) {
            this.domains = new bw_DomainsResponse(domains);
        }
        const policies = this.getResponseProperty("Policies");
        if (policies != null) {
            this.policies = policies.map((p) => new bw_PolicyResponse(p));
        }
        const sends = this.getResponseProperty("Sends");
        if (sends != null) {
            this.sends = sends.map((s) => new bw_send_response_SendResponse(s));
        }
    }
}

;// ../../libs/common/src/platform/sync/index.ts



;// ../../libs/common/src/vault/models/response/attachment-upload-data.response.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


class bw_AttachmentUploadDataResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.url = null;
        this.attachmentId = this.getResponseProperty("AttachmentId");
        this.fileUploadType = this.getResponseProperty("FileUploadType");
        const cipherResponse = this.getResponseProperty("CipherResponse");
        const cipherMiniResponse = this.getResponseProperty("CipherMiniResponse");
        this.cipherResponse = cipherResponse == null ? null : new bw_cipher_response_CipherResponse(cipherResponse);
        this.cipherMiniResponse =
            cipherMiniResponse == null ? null : new bw_cipher_response_CipherResponse(cipherMiniResponse);
        this.url = this.getResponseProperty("Url");
    }
}

;// ../../libs/common/src/vault/models/response/optional-cipher.response.ts


class bw_OptionalCipherResponse extends bw_BaseResponse {
    constructor(response) {
        super(response);
        this.unavailable = this.getResponseProperty("Unavailable");
        this.cipher = new bw_cipher_response_CipherResponse(this.getResponseProperty("Cipher"));
    }
}

;// ../../libs/common/src/services/api.service.ts
var bw_api_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






















































/**
 * @deprecated The `ApiService` class is deprecated and calls should be extracted into individual
 * api services. The `send` method is still allowed to be used within api services. For background
 * of this decision please read https://contributing.bitwarden.com/architecture/adr/refactor-api-service.
 */
class bw_ApiService {
    constructor(tokenService, platformUtilsService, environmentService, appIdService, refreshAccessTokenErrorCallback, logService, logoutCallback, vaultTimeoutSettingsService, customUserAgent = null) {
        this.tokenService = tokenService;
        this.platformUtilsService = platformUtilsService;
        this.environmentService = environmentService;
        this.appIdService = appIdService;
        this.refreshAccessTokenErrorCallback = refreshAccessTokenErrorCallback;
        this.logService = logService;
        this.logoutCallback = logoutCallback;
        this.vaultTimeoutSettingsService = vaultTimeoutSettingsService;
        this.customUserAgent = customUserAgent;
        this.isWebClient = false;
        this.isDesktopClient = false;
        this.device = platformUtilsService.getDevice();
        this.deviceType = this.device.toString();
        this.isWebClient =
            this.device === bw_DeviceType.IEBrowser ||
                this.device === bw_DeviceType.ChromeBrowser ||
                this.device === bw_DeviceType.EdgeBrowser ||
                this.device === bw_DeviceType.FirefoxBrowser ||
                this.device === bw_DeviceType.OperaBrowser ||
                this.device === bw_DeviceType.SafariBrowser ||
                this.device === bw_DeviceType.UnknownBrowser ||
                this.device === bw_DeviceType.VivaldiBrowser;
        this.isDesktopClient =
            this.device === bw_DeviceType.WindowsDesktop ||
                this.device === bw_DeviceType.MacOsDesktop ||
                this.device === bw_DeviceType.LinuxDesktop ||
                this.device === bw_DeviceType.WindowsCLI ||
                this.device === bw_DeviceType.MacOsCLI ||
                this.device === bw_DeviceType.LinuxCLI;
    }
    // Auth APIs
    postIdentityToken(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            var _a;
            const headers = new Headers({
                "Content-Type": "application/x-www-form-urlencoded; charset=utf-8",
                Accept: "application/json",
                "Device-Type": this.deviceType,
            });
            if (this.customUserAgent != null) {
                headers.set("User-Agent", this.customUserAgent);
            }
            request.alterIdentityTokenHeaders(headers);
            const identityToken = request instanceof bw_UserApiTokenRequest
                ? request.toIdentityToken()
                : request.toIdentityToken(this.platformUtilsService.getClientType());
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const response = yield this.fetch(new Request(env.getIdentityUrl() + "/connect/token", {
                body: this.qsStringify(identityToken),
                credentials: yield this.getCredentials(),
                cache: "no-store",
                headers: headers,
                method: "POST",
            }));
            let responseJson = null;
            if (this.isJsonResponse(response)) {
                responseJson = yield response.json();
            }
            if (responseJson != null) {
                if (response.status === 200) {
                    return new bw_IdentityTokenResponse(responseJson);
                }
                else if (response.status === 400 &&
                    responseJson.TwoFactorProviders2 &&
                    Object.keys(responseJson.TwoFactorProviders2).length) {
                    return new bw_IdentityTwoFactorResponse(responseJson);
                }
                else if (response.status === 400 &&
                    responseJson.HCaptcha_SiteKey &&
                    Object.keys(responseJson.HCaptcha_SiteKey).length) {
                    return new bw_IdentityCaptchaResponse(responseJson);
                }
                else if (response.status === 400 &&
                    ((_a = responseJson === null || responseJson === void 0 ? void 0 : responseJson.ErrorModel) === null || _a === void 0 ? void 0 : _a.Message) === bw_ApiService.NEW_DEVICE_VERIFICATION_REQUIRED_MESSAGE) {
                    return new bw_IdentityDeviceVerificationResponse(responseJson);
                }
            }
            return Promise.reject(new bw_ErrorResponse(responseJson, response.status, true));
        });
    }
    refreshIdentityToken() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            try {
                yield this.refreshToken();
            }
            catch (e) {
                this.logService.error("Error refreshing access token: ", e);
                throw e;
            }
        });
    }
    // TODO: PM-3519: Create and move to AuthRequest Api service
    getAuthRequest(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const path = `/auth-requests/${id}`;
            const r = yield this.send("GET", path, null, true, true);
            return new bw_auth_request_response_AuthRequestResponse(r);
        });
    }
    putAuthRequest(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const path = `/auth-requests/${id}`;
            const r = yield this.send("PUT", path, request, true, true);
            return new bw_auth_request_response_AuthRequestResponse(r);
        });
    }
    getAuthRequests() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const path = `/auth-requests/`;
            const r = yield this.send("GET", path, null, true, true);
            return new bw_ListResponse(r, bw_auth_request_response_AuthRequestResponse);
        });
    }
    getLastAuthRequest() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const requests = yield this.getAuthRequests();
            const activeRequests = requests.data.filter((m) => !m.isAnswered && !m.isExpired);
            const lastRequest = activeRequests.sort((a, b) => a.creationDate.localeCompare(b.creationDate))[activeRequests.length - 1];
            return lastRequest;
        });
    }
    // Account APIs
    getProfile() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/accounts/profile", null, true, true);
            return new bw_ProfileResponse(r);
        });
    }
    getUserSubscription() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/accounts/subscription", null, true, true);
            return new bw_SubscriptionResponse(r);
        });
    }
    getTaxInfo() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/accounts/tax", null, true, true);
            return new bw_TaxInfoResponse(r);
        });
    }
    putProfile(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/accounts/profile", request, true, true);
            return new bw_ProfileResponse(r);
        });
    }
    putAvatar(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/accounts/avatar", request, true, true);
            return new bw_ProfileResponse(r);
        });
    }
    putTaxInfo(request) {
        return this.send("PUT", "/accounts/tax", request, true, false);
    }
    postPrelogin(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const r = yield this.send("POST", "/accounts/prelogin", request, false, true, env.getIdentityUrl());
            return new bw_PreloginResponse(r);
        });
    }
    postEmailToken(request) {
        return this.send("POST", "/accounts/email-token", request, true, false);
    }
    postEmail(request) {
        return this.send("POST", "/accounts/email", request, true, false);
    }
    postSetKeyConnectorKey(request) {
        return this.send("POST", "/accounts/set-key-connector-key", request, true, false);
    }
    postSecurityStamp(request) {
        return this.send("POST", "/accounts/security-stamp", request, true, false);
    }
    getAccountRevisionDate() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/accounts/revision-date", null, true, true);
            return r;
        });
    }
    postPasswordHint(request) {
        return this.send("POST", "/accounts/password-hint", request, false, false);
    }
    postRegister(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const r = yield this.send("POST", "/accounts/register", request, false, true, env.getIdentityUrl());
            return new bw_RegisterResponse(r);
        });
    }
    postPremium(data) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/accounts/premium", data, true, true);
            return new bw_PaymentResponse(r);
        });
    }
    postReinstatePremium() {
        return this.send("POST", "/accounts/reinstate-premium", null, true, false);
    }
    postAccountStorage(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/accounts/storage", request, true, true);
            return new bw_PaymentResponse(r);
        });
    }
    postAccountPayment(request) {
        return this.send("POST", "/accounts/payment", request, true, false);
    }
    postAccountLicense(data) {
        return this.send("POST", "/accounts/license", data, true, false);
    }
    postAccountKeys(request) {
        return this.send("POST", "/accounts/keys", request, true, false);
    }
    postAccountVerifyEmail() {
        return this.send("POST", "/accounts/verify-email", null, true, false);
    }
    postAccountVerifyEmailToken(request) {
        return this.send("POST", "/accounts/verify-email-token", request, false, false);
    }
    postAccountRecoverDelete(request) {
        return this.send("POST", "/accounts/delete-recover", request, false, false);
    }
    postAccountRecoverDeleteToken(request) {
        return this.send("POST", "/accounts/delete-recover-token", request, false, false);
    }
    postAccountKdf(request) {
        return this.send("POST", "/accounts/kdf", request, true, false);
    }
    deleteSsoUser(organizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return this.send("DELETE", "/accounts/sso/" + organizationId, null, true, false);
        });
    }
    getSsoUserIdentifier() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return this.send("GET", "/accounts/sso/user-identifier", null, true, true);
        });
    }
    postUserApiKey(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/accounts/api-key", request, true, true);
            return new bw_ApiKeyResponse(r);
        });
    }
    postUserRotateApiKey(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/accounts/rotate-api-key", request, true, true);
            return new bw_ApiKeyResponse(r);
        });
    }
    postConvertToKeyConnector() {
        return this.send("POST", "/accounts/convert-to-key-connector", null, true, false);
    }
    // Account Billing APIs
    getUserBillingHistory() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/accounts/billing/history", null, true, true);
            return new bw_BillingHistoryResponse(r);
        });
    }
    getUserBillingPayment() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/accounts/billing/payment-method", null, true, true);
            return new bw_BillingPaymentResponse(r);
        });
    }
    // Cipher APIs
    getCipher(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/ciphers/" + id, null, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    getFullCipherDetails(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/ciphers/" + id + "/details", null, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    getCipherAdmin(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/ciphers/" + id + "/admin", null, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    getCiphersOrganization(organizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/ciphers/organization-details?organizationId=" + organizationId, null, true, true);
            return new bw_ListResponse(r, bw_cipher_response_CipherResponse);
        });
    }
    postCipher(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/ciphers", request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    postCipherCreate(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/ciphers/create", request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    postCipherAdmin(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/ciphers/admin", request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    putCipher(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/" + id, request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    putPartialCipher(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/" + id + "/partial", request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    putCipherAdmin(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/" + id + "/admin", request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    deleteCipher(id) {
        return this.send("DELETE", "/ciphers/" + id, null, true, false);
    }
    deleteCipherAdmin(id) {
        return this.send("DELETE", "/ciphers/" + id + "/admin", null, true, false);
    }
    deleteManyCiphers(request) {
        return this.send("DELETE", "/ciphers", request, true, false);
    }
    deleteManyCiphersAdmin(request) {
        return this.send("DELETE", "/ciphers/admin", request, true, false);
    }
    putMoveCiphers(request) {
        return this.send("PUT", "/ciphers/move", request, true, false);
    }
    putShareCipher(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/" + id + "/share", request, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    putShareCiphers(request) {
        return this.send("PUT", "/ciphers/share", request, true, false);
    }
    putCipherCollections(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.send("PUT", "/ciphers/" + id + "/collections_v2", request, true, true);
            return new bw_OptionalCipherResponse(response);
        });
    }
    putCipherCollectionsAdmin(id, request) {
        return this.send("PUT", "/ciphers/" + id + "/collections-admin", request, true, true);
    }
    postPurgeCiphers(request, organizationId = null) {
        let path = "/ciphers/purge";
        if (organizationId != null) {
            path += "?organizationId=" + organizationId;
        }
        return this.send("POST", path, request, true, false);
    }
    putDeleteCipher(id) {
        return this.send("PUT", "/ciphers/" + id + "/delete", null, true, false);
    }
    putDeleteCipherAdmin(id) {
        return this.send("PUT", "/ciphers/" + id + "/delete-admin", null, true, false);
    }
    putDeleteManyCiphers(request) {
        return this.send("PUT", "/ciphers/delete", request, true, false);
    }
    putDeleteManyCiphersAdmin(request) {
        return this.send("PUT", "/ciphers/delete-admin", request, true, false);
    }
    putRestoreCipher(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/" + id + "/restore", null, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    putRestoreCipherAdmin(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/" + id + "/restore-admin", null, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    putRestoreManyCiphers(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/restore", request, true, true);
            return new bw_ListResponse(r, bw_cipher_response_CipherResponse);
        });
    }
    putRestoreManyCiphersAdmin(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/ciphers/restore-admin", request, true, true);
            return new bw_ListResponse(r, bw_cipher_response_CipherResponse);
        });
    }
    // Attachments APIs
    getAttachmentData(cipherId, attachmentId, emergencyAccessId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const path = (emergencyAccessId != null ? "/emergency-access/" + emergencyAccessId + "/" : "/ciphers/") +
                cipherId +
                "/attachment/" +
                attachmentId;
            const r = yield this.send("GET", path, null, true, true);
            return new bw_attachment_response_AttachmentResponse(r);
        });
    }
    postCipherAttachment(id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/ciphers/" + id + "/attachment/v2", request, true, true);
            return new bw_AttachmentUploadDataResponse(r);
        });
    }
    /**
     * @deprecated Mar 25 2021: This method has been deprecated in favor of direct uploads.
     * This method still exists for backward compatibility with old server versions.
     */
    postCipherAttachmentLegacy(id, data) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/ciphers/" + id + "/attachment", data, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    /**
     * @deprecated Mar 25 2021: This method has been deprecated in favor of direct uploads.
     * This method still exists for backward compatibility with old server versions.
     */
    postCipherAttachmentAdminLegacy(id, data) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/ciphers/" + id + "/attachment-admin", data, true, true);
            return new bw_cipher_response_CipherResponse(r);
        });
    }
    deleteCipherAttachment(id, attachmentId) {
        return this.send("DELETE", "/ciphers/" + id + "/attachment/" + attachmentId, null, true, true);
    }
    deleteCipherAttachmentAdmin(id, attachmentId) {
        return this.send("DELETE", "/ciphers/" + id + "/attachment/" + attachmentId + "/admin", null, true, false);
    }
    postShareCipherAttachment(id, attachmentId, data, organizationId) {
        return this.send("POST", "/ciphers/" + id + "/attachment/" + attachmentId + "/share?organizationId=" + organizationId, data, true, false);
    }
    renewAttachmentUploadUrl(id, attachmentId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/ciphers/" + id + "/attachment/" + attachmentId + "/renew", null, true, true);
            return new bw_AttachmentUploadDataResponse(r);
        });
    }
    postAttachmentFile(id, attachmentId, data) {
        return this.send("POST", "/ciphers/" + id + "/attachment/" + attachmentId, data, true, false);
    }
    // Collections APIs
    getCollectionAccessDetails(organizationId, id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/collections/" + id + "/details", null, true, true);
            return new bw_CollectionAccessDetailsResponse(r);
        });
    }
    getUserCollections() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/collections", null, true, true);
            return new bw_ListResponse(r, bw_CollectionResponse);
        });
    }
    getCollections(organizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/collections", null, true, true);
            return new bw_ListResponse(r, bw_CollectionResponse);
        });
    }
    getManyCollectionsWithAccessDetails(organizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/collections/details", null, true, true);
            return new bw_ListResponse(r, bw_CollectionAccessDetailsResponse);
        });
    }
    getCollectionUsers(organizationId, id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/collections/" + id + "/users", null, true, true);
            return r.map((dr) => new bw_SelectionReadOnlyResponse(dr));
        });
    }
    postCollection(organizationId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/organizations/" + organizationId + "/collections", request, true, true);
            return new bw_CollectionAccessDetailsResponse(r);
        });
    }
    putCollection(organizationId, id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/organizations/" + organizationId + "/collections/" + id, request, true, true);
            return new bw_CollectionAccessDetailsResponse(r);
        });
    }
    putCollectionUsers(organizationId, id, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            yield this.send("PUT", "/organizations/" + organizationId + "/collections/" + id + "/users", request, true, false);
        });
    }
    deleteCollection(organizationId, id) {
        return this.send("DELETE", "/organizations/" + organizationId + "/collections/" + id, null, true, false);
    }
    deleteManyCollections(organizationId, collectionIds) {
        return this.send("DELETE", "/organizations/" + organizationId + "/collections", new bw_CollectionBulkDeleteRequest(collectionIds), true, false);
    }
    deleteCollectionUser(organizationId, id, organizationUserId) {
        return this.send("DELETE", "/organizations/" + organizationId + "/collections/" + id + "/user/" + organizationUserId, null, true, false);
    }
    // Groups APIs
    getGroupUsers(organizationId, id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/groups/" + id + "/users", null, true, true);
            return r;
        });
    }
    deleteGroupUser(organizationId, id, organizationUserId) {
        return this.send("DELETE", "/organizations/" + organizationId + "/groups/" + id + "/user/" + organizationUserId, null, true, false);
    }
    // Plan APIs
    getPlans() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/plans", null, false, true);
            return new bw_ListResponse(r, bw_PlanResponse);
        });
    }
    // Settings APIs
    getSettingsDomains() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/settings/domains", null, true, true);
            return new bw_DomainsResponse(r);
        });
    }
    putSettingsDomains(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/settings/domains", request, true, true);
            return new bw_DomainsResponse(r);
        });
    }
    // Sync APIs
    getSync() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const path = this.isDesktopClient || this.isWebClient ? "/sync?excludeDomains=true" : "/sync";
            const r = yield this.send("GET", path, null, true, true);
            return new bw_SyncResponse(r);
        });
    }
    // Two-factor APIs
    getTwoFactorProviders() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/two-factor", null, true, true);
            return new bw_ListResponse(r, bw_TwoFactorProviderResponse);
        });
    }
    getTwoFactorOrganizationProviders(organizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/two-factor", null, true, true);
            return new bw_ListResponse(r, bw_TwoFactorProviderResponse);
        });
    }
    getTwoFactorAuthenticator(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-authenticator", request, true, true);
            return new bw_TwoFactorAuthenticatorResponse(r);
        });
    }
    getTwoFactorEmail(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-email", request, true, true);
            return new bw_TwoFactorEmailResponse(r);
        });
    }
    getTwoFactorDuo(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-duo", request, true, true);
            return new bw_TwoFactorDuoResponse(r);
        });
    }
    getTwoFactorOrganizationDuo(organizationId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/organizations/" + organizationId + "/two-factor/get-duo", request, true, true);
            return new bw_TwoFactorDuoResponse(r);
        });
    }
    getTwoFactorYubiKey(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-yubikey", request, true, true);
            return new bw_TwoFactorYubiKeyResponse(r);
        });
    }
    getTwoFactorWebAuthn(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-webauthn", request, true, true);
            return new bw_TwoFactorWebAuthnResponse(r);
        });
    }
    getTwoFactorWebAuthnChallenge(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-webauthn-challenge", request, true, true);
            return new bw_ChallengeResponse(r);
        });
    }
    getTwoFactorRecover(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/two-factor/get-recover", request, true, true);
            return new bw_TwoFactorRecoverResponse(r);
        });
    }
    putTwoFactorAuthenticator(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/two-factor/authenticator", request, true, true);
            return new bw_TwoFactorAuthenticatorResponse(r);
        });
    }
    deleteTwoFactorAuthenticator(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("DELETE", "/two-factor/authenticator", request, true, true);
            return new bw_TwoFactorProviderResponse(r);
        });
    }
    putTwoFactorEmail(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/two-factor/email", request, true, true);
            return new bw_TwoFactorEmailResponse(r);
        });
    }
    putTwoFactorDuo(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/two-factor/duo", request, true, true);
            return new bw_TwoFactorDuoResponse(r);
        });
    }
    putTwoFactorOrganizationDuo(organizationId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/organizations/" + organizationId + "/two-factor/duo", request, true, true);
            return new bw_TwoFactorDuoResponse(r);
        });
    }
    putTwoFactorYubiKey(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/two-factor/yubikey", request, true, true);
            return new bw_TwoFactorYubiKeyResponse(r);
        });
    }
    putTwoFactorWebAuthn(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const response = request.deviceResponse.response;
            const data = Object.assign({}, request);
            data.deviceResponse = {
                id: request.deviceResponse.id,
                rawId: btoa(request.deviceResponse.id),
                type: request.deviceResponse.type,
                extensions: request.deviceResponse.getClientExtensionResults(),
                response: {
                    AttestationObject: bw_utils_Utils.fromBufferToB64(response.attestationObject),
                    clientDataJson: bw_utils_Utils.fromBufferToB64(response.clientDataJSON),
                },
            };
            const r = yield this.send("PUT", "/two-factor/webauthn", data, true, true);
            return new bw_TwoFactorWebAuthnResponse(r);
        });
    }
    deleteTwoFactorWebAuthn(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("DELETE", "/two-factor/webauthn", request, true, true);
            return new bw_TwoFactorWebAuthnResponse(r);
        });
    }
    putTwoFactorDisable(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/two-factor/disable", request, true, true);
            return new bw_TwoFactorProviderResponse(r);
        });
    }
    putTwoFactorOrganizationDisable(organizationId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/organizations/" + organizationId + "/two-factor/disable", request, true, true);
            return new bw_TwoFactorProviderResponse(r);
        });
    }
    postTwoFactorEmailSetup(request) {
        return this.send("POST", "/two-factor/send-email", request, true, false);
    }
    postTwoFactorEmail(request) {
        return this.send("POST", "/two-factor/send-email-login", request, false, false);
    }
    getDeviceVerificationSettings() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/two-factor/get-device-verification-settings", null, true, true);
            return new bw_DeviceVerificationResponse(r);
        });
    }
    putDeviceVerificationSettings(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/two-factor/device-verification-settings", request, true, true);
            return new bw_DeviceVerificationResponse(r);
        });
    }
    // Organization APIs
    getCloudCommunicationsEnabled() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/connections/enabled", null, true, true);
            return r;
        });
    }
    getOrganizationConnection(id, type, configType) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", `/organizations/connections/${id}/${type}`, null, true, true);
            return new bw_OrganizationConnectionResponse(r, configType);
        });
    }
    createOrganizationConnection(request, configType) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/organizations/connections/", request, true, true);
            return new bw_OrganizationConnectionResponse(r, configType);
        });
    }
    updateOrganizationConnection(request, configType, organizationConnectionId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("PUT", "/organizations/connections/" + organizationConnectionId, request, true, true);
            return new bw_OrganizationConnectionResponse(r, configType);
        });
    }
    deleteOrganizationConnection(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return this.send("DELETE", "/organizations/connections/" + id, null, true, false);
        });
    }
    // Provider User APIs
    getProviderUsers(providerId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/providers/" + providerId + "/users", null, true, true);
            return new bw_ListResponse(r, bw_ProviderUserUserDetailsResponse);
        });
    }
    getProviderUser(providerId, id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/providers/" + providerId + "/users/" + id, null, true, true);
            return new bw_ProviderUserResponse(r);
        });
    }
    postProviderUserInvite(providerId, request) {
        return this.send("POST", "/providers/" + providerId + "/users/invite", request, true, false);
    }
    postProviderUserReinvite(providerId, id) {
        return this.send("POST", "/providers/" + providerId + "/users/" + id + "/reinvite", null, true, false);
    }
    postManyProviderUserReinvite(providerId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/providers/" + providerId + "/users/reinvite", request, true, true);
            return new bw_ListResponse(r, bw_ProviderUserBulkResponse);
        });
    }
    postProviderUserBulkConfirm(providerId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/providers/" + providerId + "/users/confirm", request, true, true);
            return new bw_ListResponse(r, bw_ProviderUserBulkResponse);
        });
    }
    deleteManyProviderUsers(providerId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("DELETE", "/providers/" + providerId + "/users", request, true, true);
            return new bw_ListResponse(r, bw_ProviderUserBulkResponse);
        });
    }
    postProviderUserAccept(providerId, id, request) {
        return this.send("POST", "/providers/" + providerId + "/users/" + id + "/accept", request, true, false);
    }
    postProviderUserConfirm(providerId, id, request) {
        return this.send("POST", "/providers/" + providerId + "/users/" + id + "/confirm", request, true, false);
    }
    postProviderUsersPublicKey(providerId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/providers/" + providerId + "/users/public-keys", request, true, true);
            return new bw_ListResponse(r, bw_ProviderUserBulkPublicKeyResponse);
        });
    }
    putProviderUser(providerId, id, request) {
        return this.send("PUT", "/providers/" + providerId + "/users/" + id, request, true, false);
    }
    deleteProviderUser(providerId, id) {
        return this.send("DELETE", "/providers/" + providerId + "/users/" + id, null, true, false);
    }
    // Provider Organization APIs
    getProviderClients(providerId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/providers/" + providerId + "/organizations", null, true, true);
            return new bw_ListResponse(r, bw_ProviderOrganizationOrganizationDetailsResponse);
        });
    }
    postProviderAddOrganization(providerId, request) {
        return this.send("POST", "/providers/" + providerId + "/organizations/add", request, true, false);
    }
    postProviderCreateOrganization(providerId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/providers/" + providerId + "/organizations", request, true, true);
            return new bw_ProviderOrganizationResponse(r);
        });
    }
    deleteProviderOrganization(providerId, id) {
        return this.send("DELETE", "/providers/" + providerId + "/organizations/" + id, null, true, false);
    }
    // Event APIs
    getEvents(start, end, token) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", this.addEventParameters("/events", start, end, token), null, true, true);
            return new bw_ListResponse(r, bw_EventResponse);
        });
    }
    getEventsCipher(id, start, end, token) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", this.addEventParameters("/ciphers/" + id + "/events", start, end, token), null, true, true);
            return new bw_ListResponse(r, bw_EventResponse);
        });
    }
    getEventsOrganization(id, start, end, token) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", this.addEventParameters("/organizations/" + id + "/events", start, end, token), null, true, true);
            return new bw_ListResponse(r, bw_EventResponse);
        });
    }
    getEventsOrganizationUser(organizationId, id, start, end, token) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", this.addEventParameters("/organizations/" + organizationId + "/users/" + id + "/events", start, end, token), null, true, true);
            return new bw_ListResponse(r, bw_EventResponse);
        });
    }
    getEventsProvider(id, start, end, token) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", this.addEventParameters("/providers/" + id + "/events", start, end, token), null, true, true);
            return new bw_ListResponse(r, bw_EventResponse);
        });
    }
    getEventsProviderUser(providerId, id, start, end, token) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", this.addEventParameters("/providers/" + providerId + "/users/" + id + "/events", start, end, token), null, true, true);
            return new bw_ListResponse(r, bw_EventResponse);
        });
    }
    postEventsCollect(request, userId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const authHeader = yield this.tokenService.getAccessToken(userId);
            const headers = new Headers({
                "Device-Type": this.deviceType,
                Authorization: "Bearer " + authHeader,
                "Content-Type": "application/json; charset=utf-8",
            });
            if (this.customUserAgent != null) {
                headers.set("User-Agent", this.customUserAgent);
            }
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const response = yield this.fetch(new Request(env.getEventsUrl() + "/collect", {
                cache: "no-store",
                credentials: yield this.getCredentials(),
                method: "POST",
                body: JSON.stringify(request),
                headers: headers,
            }));
            if (response.status !== 200) {
                return Promise.reject("Event post failed.");
            }
        });
    }
    // User APIs
    getUserPublicKey(id) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/users/" + id + "/public-key", null, true, true);
            return new bw_UserKeyResponse(r);
        });
    }
    // HIBP APIs
    getHibpBreach(username) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/hibp/breach?username=" + username, null, true, true);
            return r.map((a) => new bw_BreachAccountResponse(a));
        });
    }
    // Misc
    postBitPayInvoice(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/bitpay-invoice", request, true, true);
            return r;
        });
    }
    postSetupPayment() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("POST", "/setup-payment", null, true, true);
            return r;
        });
    }
    // Key Connector
    getMasterKeyFromKeyConnector(keyConnectorUrl) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const authHeader = yield this.getActiveBearerToken();
            const response = yield this.fetch(new Request(keyConnectorUrl + "/user-keys", {
                cache: "no-store",
                method: "GET",
                headers: new Headers({
                    Accept: "application/json",
                    Authorization: "Bearer " + authHeader,
                }),
            }));
            if (response.status !== 200) {
                const error = yield this.handleError(response, false, true);
                return Promise.reject(error);
            }
            return new bw_KeyConnectorUserKeyResponse(yield response.json());
        });
    }
    postUserKeyToKeyConnector(keyConnectorUrl, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const authHeader = yield this.getActiveBearerToken();
            const response = yield this.fetch(new Request(keyConnectorUrl + "/user-keys", {
                cache: "no-store",
                method: "POST",
                headers: new Headers({
                    Accept: "application/json",
                    Authorization: "Bearer " + authHeader,
                    "Content-Type": "application/json; charset=utf-8",
                }),
                body: JSON.stringify(request),
            }));
            if (response.status !== 200) {
                const error = yield this.handleError(response, false, true);
                return Promise.reject(error);
            }
        });
    }
    getKeyConnectorAlive(keyConnectorUrl) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.fetch(new Request(keyConnectorUrl + "/alive", {
                cache: "no-store",
                method: "GET",
                headers: new Headers({
                    Accept: "application/json",
                    "Content-Type": "application/json; charset=utf-8",
                }),
            }));
            if (response.status !== 200) {
                const error = yield this.handleError(response, false, true);
                return Promise.reject(error);
            }
        });
    }
    getOrganizationExport(organizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const r = yield this.send("GET", "/organizations/" + organizationId + "/export", null, true, true);
            return new bw_OrganizationExportResponse(r);
        });
    }
    // Helpers
    getActiveBearerToken() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            let accessToken = yield this.tokenService.getAccessToken();
            if (yield this.tokenService.tokenNeedsRefresh()) {
                accessToken = yield this.refreshToken();
            }
            return accessToken;
        });
    }
    fetch(request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            if (request.method === "GET") {
                request.headers.set("Cache-Control", "no-store");
                request.headers.set("Pragma", "no-cache");
            }
            request.headers.set("Bitwarden-Client-Name", this.platformUtilsService.getClientType());
            request.headers.set("Bitwarden-Client-Version", yield this.platformUtilsService.getApplicationVersionNumber());
            return this.nativeFetch(request);
        });
    }
    nativeFetch(request) {
        return fetch(request);
    }
    preValidateSso(identifier) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            if (identifier == null || identifier === "") {
                throw new Error("Organization Identifier was not provided.");
            }
            const headers = new Headers({
                Accept: "application/json",
                "Device-Type": this.deviceType,
            });
            if (this.customUserAgent != null) {
                headers.set("User-Agent", this.customUserAgent);
            }
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const path = `/sso/prevalidate?domainHint=${encodeURIComponent(identifier)}`;
            const response = yield this.fetch(new Request(env.getIdentityUrl() + path, {
                cache: "no-store",
                credentials: yield this.getCredentials(),
                headers: headers,
                method: "GET",
            }));
            if (response.status === 200) {
                const body = yield response.json();
                return new bw_SsoPreValidateResponse(body);
            }
            else {
                const error = yield this.handleError(response, false, true);
                return Promise.reject(error);
            }
        });
    }
    postCreateSponsorship(sponsoredOrgId, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.send("POST", "/organization/sponsorship/" +
                (this.platformUtilsService.isSelfHost() ? "self-hosted/" : "") +
                sponsoredOrgId +
                "/families-for-enterprise", request, true, false);
        });
    }
    getSponsorshipSyncStatus(sponsoredOrgId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.send("GET", "/organization/sponsorship/" + sponsoredOrgId + "/sync-status", null, true, true);
            return new bw_OrganizationSponsorshipSyncStatusResponse(response);
        });
    }
    deleteRevokeSponsorship(sponsoringOrganizationId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.send("DELETE", "/organization/sponsorship/" +
                (this.platformUtilsService.isSelfHost() ? "self-hosted/" : "") +
                sponsoringOrganizationId, null, true, false);
        });
    }
    deleteRemoveSponsorship(sponsoringOrgId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.send("DELETE", "/organization/sponsorship/sponsored/" + sponsoringOrgId, null, true, false);
        });
    }
    postPreValidateSponsorshipToken(sponsorshipToken) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const response = yield this.send("POST", "/organization/sponsorship/validate-token?sponsorshipToken=" +
                encodeURIComponent(sponsorshipToken), null, true, true);
            return new bw_PreValidateSponsorshipResponse(response);
        });
    }
    postRedeemSponsorship(sponsorshipToken, request) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.send("POST", "/organization/sponsorship/redeem?sponsorshipToken=" + encodeURIComponent(sponsorshipToken), request, true, false);
        });
    }
    postResendSponsorshipOffer(sponsoringOrgId) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            return yield this.send("POST", "/organization/sponsorship/" + sponsoringOrgId + "/families-for-enterprise/resend", null, true, false);
        });
    }
    // Keep the running refreshTokenPromise to prevent parallel calls.
    refreshToken() {
        if (this.refreshTokenPromise === undefined) {
            this.refreshTokenPromise = this.internalRefreshToken();
            void this.refreshTokenPromise.finally(() => {
                this.refreshTokenPromise = undefined;
            });
        }
        return this.refreshTokenPromise;
    }
    internalRefreshToken() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const refreshToken = yield this.tokenService.getRefreshToken();
            if (refreshToken != null && refreshToken !== "") {
                return this.refreshAccessToken();
            }
            const clientId = yield this.tokenService.getClientId();
            const clientSecret = yield this.tokenService.getClientSecret();
            if (!bw_utils_Utils.isNullOrWhitespace(clientId) && !bw_utils_Utils.isNullOrWhitespace(clientSecret)) {
                return this.refreshApiToken();
            }
            this.refreshAccessTokenErrorCallback();
            throw new Error("Cannot refresh access token, no refresh token or api keys are stored.");
        });
    }
    refreshAccessToken() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const refreshToken = yield this.tokenService.getRefreshToken();
            if (refreshToken == null || refreshToken === "") {
                throw new Error();
            }
            const headers = new Headers({
                "Content-Type": "application/x-www-form-urlencoded; charset=utf-8",
                Accept: "application/json",
                "Device-Type": this.deviceType,
            });
            if (this.customUserAgent != null) {
                headers.set("User-Agent", this.customUserAgent);
            }
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            const decodedToken = yield this.tokenService.decodeAccessToken();
            const response = yield this.fetch(new Request(env.getIdentityUrl() + "/connect/token", {
                body: this.qsStringify({
                    grant_type: "refresh_token",
                    client_id: decodedToken.client_id,
                    refresh_token: refreshToken,
                }),
                cache: "no-store",
                credentials: yield this.getCredentials(),
                headers: headers,
                method: "POST",
            }));
            if (response.status === 200) {
                const responseJson = yield response.json();
                const tokenResponse = new bw_IdentityTokenResponse(responseJson);
                const newDecodedAccessToken = yield this.tokenService.decodeAccessToken(tokenResponse.accessToken);
                const userId = newDecodedAccessToken.sub;
                const vaultTimeoutAction = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutActionByUserId$(userId));
                const vaultTimeout = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutByUserId$(userId));
                const refreshedTokens = yield this.tokenService.setTokens(tokenResponse.accessToken, vaultTimeoutAction, vaultTimeout, tokenResponse.refreshToken);
                return refreshedTokens.accessToken;
            }
            else {
                const error = yield this.handleError(response, true, true);
                return Promise.reject(error);
            }
        });
    }
    refreshApiToken() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const clientId = yield this.tokenService.getClientId();
            const clientSecret = yield this.tokenService.getClientSecret();
            const appId = yield this.appIdService.getAppId();
            const deviceRequest = new bw_DeviceRequest(appId, this.platformUtilsService);
            const tokenRequest = new bw_UserApiTokenRequest(clientId, clientSecret, new bw_TokenTwoFactorRequest(), deviceRequest);
            const response = yield this.postIdentityToken(tokenRequest);
            if (!(response instanceof bw_IdentityTokenResponse)) {
                throw new Error("Invalid response received when refreshing api token");
            }
            const newDecodedAccessToken = yield this.tokenService.decodeAccessToken(response.accessToken);
            const userId = newDecodedAccessToken.sub;
            const vaultTimeoutAction = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutActionByUserId$(userId));
            const vaultTimeout = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.vaultTimeoutSettingsService.getVaultTimeoutByUserId$(userId));
            const refreshedToken = yield this.tokenService.setAccessToken(response.accessToken, vaultTimeoutAction, vaultTimeout);
            return refreshedToken;
        });
    }
    send(method, path, body, authed, hasResponse, apiUrl, alterHeaders) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            apiUrl = bw_utils_Utils.isNullOrWhitespace(apiUrl) ? env.getApiUrl() : apiUrl;
            // Prevent directory traversal from malicious paths
            const pathParts = path.split("?");
            const requestUrl = apiUrl + bw_utils_Utils.normalizePath(pathParts[0]) + (pathParts.length > 1 ? `?${pathParts[1]}` : "");
            const [requestHeaders, requestBody] = yield this.buildHeadersAndBody(authed, hasResponse, body, alterHeaders);
            const requestInit = {
                cache: "no-store",
                credentials: yield this.getCredentials(),
                method: method,
            };
            requestInit.headers = requestHeaders;
            requestInit.body = requestBody;
            const response = yield this.fetch(new Request(requestUrl, requestInit));
            const responseType = response.headers.get("content-type");
            const responseIsJson = responseType != null && responseType.indexOf("application/json") !== -1;
            const responseIsCsv = responseType != null && responseType.indexOf("text/csv") !== -1;
            if (hasResponse && response.status === 200 && responseIsJson) {
                const responseJson = yield response.json();
                return responseJson;
            }
            else if (hasResponse && response.status === 200 && responseIsCsv) {
                return yield response.text();
            }
            else if (response.status !== 200 && response.status !== 204) {
                const error = yield this.handleError(response, false, authed);
                return Promise.reject(error);
            }
        });
    }
    buildHeadersAndBody(authed, hasResponse, body, alterHeaders) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            let requestBody = null;
            const headers = new Headers({
                "Device-Type": this.deviceType,
            });
            if (bw_flagEnabled("prereleaseBuild")) {
                headers.set("Is-Prerelease", "1");
            }
            if (this.customUserAgent != null) {
                headers.set("User-Agent", this.customUserAgent);
            }
            if (hasResponse) {
                headers.set("Accept", "application/json");
            }
            if (alterHeaders != null) {
                alterHeaders(headers);
            }
            if (authed) {
                const authHeader = yield this.getActiveBearerToken();
                headers.set("Authorization", "Bearer " + authHeader);
            }
            if (body != null) {
                if (typeof body === "string") {
                    requestBody = body;
                    headers.set("Content-Type", "application/x-www-form-urlencoded; charset=utf-8");
                }
                else if (typeof body === "object") {
                    if (body instanceof FormData) {
                        requestBody = body;
                    }
                    else {
                        headers.set("Content-Type", "application/json; charset=utf-8");
                        requestBody = JSON.stringify(body);
                    }
                }
            }
            return [headers, requestBody];
        });
    }
    handleError(response, tokenError, authed) {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            let responseJson = null;
            if (this.isJsonResponse(response)) {
                responseJson = yield response.json();
            }
            else if (this.isTextResponse(response)) {
                responseJson = { Message: yield response.text() };
            }
            if (authed) {
                if (response.status === 401 ||
                    response.status === 403 ||
                    (tokenError &&
                        response.status === 400 &&
                        responseJson != null &&
                        responseJson.error === "invalid_grant")) {
                    yield this.logoutCallback("invalidGrantError");
                }
            }
            return new bw_ErrorResponse(responseJson, response.status, tokenError);
        });
    }
    qsStringify(params) {
        return Object.keys(params)
            .map((key) => {
            return encodeURIComponent(key) + "=" + encodeURIComponent(params[key]);
        })
            .join("&");
    }
    getCredentials() {
        return bw_api_service_awaiter(this, void 0, void 0, function* () {
            const env = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.environmentService.environment$);
            if (!this.isWebClient || env.hasBaseUrl()) {
                return "include";
            }
            return undefined;
        });
    }
    addEventParameters(base, start, end, token) {
        if (start != null) {
            base += "?start=" + start;
        }
        if (end != null) {
            base += base.indexOf("?") > -1 ? "&" : "?";
            base += "end=" + end;
        }
        if (token != null) {
            base += base.indexOf("?") > -1 ? "&" : "?";
            base += "continuationToken=" + token;
        }
        return base;
    }
    isJsonResponse(response) {
        const typeHeader = response.headers.get("content-type");
        return typeHeader != null && typeHeader.indexOf("application/json") > -1;
    }
    isTextResponse(response) {
        const typeHeader = response.headers.get("content-type");
        return typeHeader != null && typeHeader.indexOf("text") > -1;
    }
}
/**
 * The message (responseJson.ErrorModel.Message) that comes back from the server when a new device verification is required.
 */
bw_ApiService.NEW_DEVICE_VERIFICATION_REQUIRED_MESSAGE = "new device verification required";

;// ./src/platform/services/node-api.service.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




global.fetch = (bw_external_node_fetch_default());
global.Request = bw_external_node_fetch_namespaceObject.Request;
global.Response = bw_external_node_fetch_namespaceObject.Response;
global.Headers = bw_external_node_fetch_namespaceObject.Headers;
global.FormData = bw_external_form_data_namespaceObject;
class bw_NodeApiService extends bw_ApiService {
    constructor(tokenService, platformUtilsService, environmentService, appIdService, refreshAccessTokenErrorCallback, logService, logoutCallback, vaultTimeoutSettingsService, customUserAgent = null) {
        super(tokenService, platformUtilsService, environmentService, appIdService, refreshAccessTokenErrorCallback, logService, logoutCallback, vaultTimeoutSettingsService, customUserAgent);
    }
    nativeFetch(request) {
        const proxy = process.env.http_proxy || process.env.https_proxy;
        if (proxy) {
            request.agent = new bw_external_https_proxy_agent_namespaceObject.HttpsProxyAgent(proxy);
        }
        return fetch(request);
    }
}

;// ./src/platform/services/node-env-secure-storage.service.ts
var bw_node_env_secure_storage_service_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore




class bw_NodeEnvSecureStorageService {
    constructor(storageService, logService, encryptService) {
        this.storageService = storageService;
        this.logService = logService;
        this.encryptService = encryptService;
    }
    get valuesRequireDeserialization() {
        return true;
    }
    get updates$() {
        return (0,bw_external_rxjs_namespaceObject.throwError)(() => new Error("Secure storage implementations cannot have their updates subscribed to."));
    }
    get(key) {
        return bw_node_env_secure_storage_service_awaiter(this, void 0, void 0, function* () {
            const value = yield this.storageService.get(this.makeProtectedStorageKey(key));
            if (value == null) {
                return null;
            }
            const obj = yield this.decrypt(value);
            return obj;
        });
    }
    has(key) {
        return bw_node_env_secure_storage_service_awaiter(this, void 0, void 0, function* () {
            return (yield this.get(key)) != null;
        });
    }
    save(key, obj) {
        return bw_node_env_secure_storage_service_awaiter(this, void 0, void 0, function* () {
            if (obj == null) {
                return this.remove(key);
            }
            if (obj !== null && typeof obj !== "string") {
                throw new Error("Only string storage is allowed.");
            }
            const protectedObj = yield this.encrypt(obj);
            yield this.storageService.save(this.makeProtectedStorageKey(key), protectedObj);
        });
    }
    remove(key) {
        return bw_node_env_secure_storage_service_awaiter(this, void 0, void 0, function* () {
            yield this.storageService.remove(this.makeProtectedStorageKey(key));
            return;
        });
    }
    encrypt(plainValue) {
        return bw_node_env_secure_storage_service_awaiter(this, void 0, void 0, function* () {
            const sessionKey = this.getSessionKey();
            if (sessionKey == null) {
                throw new Error("No session key available.");
            }
            const encValue = yield this.encryptService.encryptToBytes(bw_utils_Utils.fromB64ToArray(plainValue), sessionKey);
            if (encValue == null) {
                throw new Error("Value didn't encrypt.");
            }
            return bw_utils_Utils.fromBufferToB64(encValue.buffer);
        });
    }
    decrypt(encValue) {
        return bw_node_env_secure_storage_service_awaiter(this, void 0, void 0, function* () {
            try {
                const sessionKey = this.getSessionKey();
                if (sessionKey == null) {
                    return null;
                }
                const encBuf = bw_EncArrayBuffer.fromB64(encValue);
                const decValue = yield this.encryptService.decryptToBytes(encBuf, sessionKey);
                if (decValue == null) {
                    this.logService.info("Failed to decrypt.");
                    return null;
                }
                return bw_utils_Utils.fromBufferToB64(decValue);
                // FIXME: Remove when updating file. Eslint update
                // eslint-disable-next-line @typescript-eslint/no-unused-vars
            }
            catch (e) {
                this.logService.info("Decrypt error.");
                return null;
            }
        });
    }
    getSessionKey() {
        try {
            if (process.env.BW_SESSION != null) {
                const sessionBuffer = bw_utils_Utils.fromB64ToArray(process.env.BW_SESSION);
                if (sessionBuffer != null) {
                    const sessionKey = new bw_SymmetricCryptoKey(sessionBuffer);
                    if (sessionBuffer != null) {
                        return sessionKey;
                    }
                }
            }
            // FIXME: Remove when updating file. Eslint update
            // eslint-disable-next-line @typescript-eslint/no-unused-vars
        }
        catch (e) {
            this.logService.info("Session key is invalid.");
        }
        return null;
    }
    makeProtectedStorageKey(key) {
        return "__PROTECTED__" + key;
    }
}

;// ./src/service-container/service-container.ts
var bw_service_container_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore






















































/* eslint-disable import/no-restricted-paths -- We need the implementation to inject, but generally these should not be accessed */







// eslint-disable-next-line no-restricted-imports -- Needed for service construction





























// Polyfills
global.DOMParser = new bw_external_jsdom_namespaceObject.JSDOM().window.DOMParser;
// eslint-disable-next-line
const bw_packageJson = __webpack_require__(330);
/**
 * Instantiates services and makes them available for dependency injection.
 * Any Bitwarden-licensed services should be registered here.
 */
class bw_service_container_ServiceContainer {
    constructor() {
        var _a, _b, _c;
        this.inited = false;
        let p = null;
        const relativeDataDir = bw_external_path_namespaceObject.join(bw_external_path_namespaceObject.dirname(process.execPath), "bw-data");
        if (bw_external_fs_namespaceObject.existsSync(relativeDataDir)) {
            p = relativeDataDir;
        }
        else if (process.env.BITWARDENCLI_APPDATA_DIR) {
            p = bw_external_path_namespaceObject.resolve(process.env.BITWARDENCLI_APPDATA_DIR);
        }
        else if (process.platform === "darwin") {
            p = bw_external_path_namespaceObject.join((_a = process.env.HOME) !== null && _a !== void 0 ? _a : "", "Library/Application Support/Bitwarden CLI");
        }
        else if (process.platform === "win32") {
            p = bw_external_path_namespaceObject.join((_b = process.env.APPDATA) !== null && _b !== void 0 ? _b : "", "Bitwarden CLI");
        }
        else if (process.env.XDG_CONFIG_HOME) {
            p = bw_external_path_namespaceObject.join(process.env.XDG_CONFIG_HOME, "Bitwarden CLI");
        }
        else {
            p = bw_external_path_namespaceObject.join((_c = process.env.HOME) !== null && _c !== void 0 ? _c : "", ".config/Bitwarden CLI");
        }
        const logoutCallback = () => bw_service_container_awaiter(this, void 0, void 0, function* () { return yield this.logout(); });
        this.platformUtilsService = new bw_CliPlatformUtilsService(bw_ClientType.Cli, bw_packageJson);
        this.logService = new bw_ConsoleLogService(this.platformUtilsService.isDev(), (level) => process.env.BITWARDENCLI_DEBUG !== "true" && level <= bw_LogLevelType.Info);
        this.cryptoFunctionService = new bw_NodeCryptoFunctionService();
        this.encryptService = new bw_EncryptServiceImplementation(this.cryptoFunctionService, this.logService, true);
        this.storageService = new bw_LowdbStorageService(this.logService, null, p, false, true);
        this.secureStorageService = new bw_NodeEnvSecureStorageService(this.storageService, this.logService, 
        // MAC failures for secure storage are being logged for customers today and
        // they occur when users unlock / login and refresh a session key but don't
        // export it into their environment (e.g. BW_SESSION_KEY). This leaves a stale
        // BW_SESSION key in the env which is attempted to be used to decrypt the auto
        // unlock user key which obviously fails. So, to resolve this, we will not log
        // MAC failures for secure storage.
        new bw_EncryptServiceImplementation(this.cryptoFunctionService, this.logService, false));
        this.memoryStorageService = new bw_MemoryStorageService();
        this.memoryStorageForStateProviders = new bw_memory_storage_service_MemoryStorageService();
        const storageServiceProvider = new bw_StorageServiceProvider(this.storageService, this.memoryStorageForStateProviders);
        this.globalStateProvider = new bw_DefaultGlobalStateProvider(storageServiceProvider, this.logService);
        const stateEventRegistrarService = new bw_StateEventRegistrarService(this.globalStateProvider, storageServiceProvider);
        this.stateEventRunnerService = new bw_StateEventRunnerService(this.globalStateProvider, storageServiceProvider);
        this.i18nService = new bw_I18nService("en", "./locales", this.globalStateProvider);
        this.singleUserStateProvider = new bw_DefaultSingleUserStateProvider(storageServiceProvider, stateEventRegistrarService, this.logService);
        this.messagingService = bw_MessageSender.EMPTY;
        this.accountService = new bw_AccountServiceImplementation(this.messagingService, this.logService, this.globalStateProvider, this.singleUserStateProvider);
        this.activeUserStateProvider = new bw_DefaultActiveUserStateProvider(this.accountService, this.singleUserStateProvider);
        this.derivedStateProvider = new bw_DefaultDerivedStateProvider();
        this.stateProvider = new bw_DefaultStateProvider(this.activeUserStateProvider, this.singleUserStateProvider, this.globalStateProvider, this.derivedStateProvider);
        this.environmentService = new bw_DefaultEnvironmentService(this.stateProvider, this.accountService, process.env.ADDITIONAL_REGIONS);
        this.keyGenerationService = new bw_KeyGenerationService(this.cryptoFunctionService);
        this.tokenService = new bw_TokenService(this.singleUserStateProvider, this.globalStateProvider, this.platformUtilsService.supportsSecureStorage(), this.secureStorageService, this.keyGenerationService, this.encryptService, this.logService, logoutCallback);
        const migrationRunner = new bw_MigrationRunner(this.storageService, this.logService, new bw_MigrationBuilderService(), bw_ClientType.Cli);
        this.stateService = new bw_StateService(this.storageService, this.secureStorageService, this.memoryStorageService, this.logService, new bw_StateFactory(bw_GlobalState, bw_Account), this.accountService, this.environmentService, this.tokenService, migrationRunner);
        this.masterPasswordService = new bw_MasterPasswordService(this.stateProvider, this.stateService, this.keyGenerationService, this.encryptService, this.logService);
        this.kdfConfigService = new bw_DefaultKdfConfigService(this.stateProvider);
        this.pinService = new bw_PinService(this.accountService, this.cryptoFunctionService, this.encryptService, this.kdfConfigService, this.keyGenerationService, this.logService, this.masterPasswordService, this.stateProvider, this.stateService);
        this.keyService = new bw_DefaultKeyService(this.pinService, this.masterPasswordService, this.keyGenerationService, this.cryptoFunctionService, this.encryptService, this.platformUtilsService, this.logService, this.stateService, this.accountService, this.stateProvider, this.kdfConfigService);
        this.appIdService = new bw_AppIdService(this.storageService, this.logService);
        const customUserAgent = "Bitwarden_CLI/" +
            this.platformUtilsService.getApplicationVersionSync() +
            " (" +
            this.platformUtilsService.getDeviceString().toUpperCase() +
            ")";
        this.biometricStateService = new bw_DefaultBiometricStateService(this.stateProvider);
        this.userDecryptionOptionsService = new bw_UserDecryptionOptionsService(this.stateProvider);
        this.ssoUrlService = new bw_SsoUrlService();
        this.organizationService = new bw_DefaultOrganizationService(this.stateProvider);
        this.policyService = new bw_PolicyService(this.stateProvider, this.organizationService);
        this.vaultTimeoutSettingsService = new bw_VaultTimeoutSettingsService(this.accountService, this.pinService, this.userDecryptionOptionsService, this.keyService, this.tokenService, this.policyService, this.biometricStateService, this.stateProvider, this.logService, bw_VaultTimeoutStringType.Never);
        const refreshAccessTokenErrorCallback = () => {
            throw new Error("Refresh Access token error");
        };
        this.apiService = new bw_NodeApiService(this.tokenService, this.platformUtilsService, this.environmentService, this.appIdService, refreshAccessTokenErrorCallback, this.logService, logoutCallback, this.vaultTimeoutSettingsService, customUserAgent);
        this.containerService = new bw_ContainerService(this.keyService, this.encryptService);
        this.configApiService = new bw_ConfigApiService(this.apiService, this.tokenService);
        this.authService = new bw_AuthService(this.accountService, this.messagingService, this.keyService, this.apiService, this.stateService, this.tokenService);
        this.configService = new bw_DefaultConfigService(this.configApiService, this.environmentService, this.logService, this.stateProvider, this.authService);
        this.domainSettingsService = new bw_DefaultDomainSettingsService(this.stateProvider, this.configService);
        this.fileUploadService = new bw_FileUploadService(this.logService, this.apiService);
        this.sendStateProvider = new bw_SendStateProvider(this.stateProvider);
        this.sendService = new bw_SendService(this.keyService, this.i18nService, this.keyGenerationService, this.sendStateProvider, this.encryptService);
        this.cipherFileUploadService = new bw_CipherFileUploadService(this.apiService, this.fileUploadService);
        this.sendApiService = this.sendApiService = new bw_SendApiService(this.apiService, this.fileUploadService, this.sendService);
        this.searchService = new bw_SearchService(this.logService, this.i18nService, this.stateProvider);
        this.collectionService = new bw_DefaultCollectionService(this.keyService, this.encryptService, this.i18nService, this.stateProvider);
        this.providerService = new bw_ProviderService(this.stateProvider);
        this.policyApiService = new bw_PolicyApiService(this.policyService, this.apiService);
        this.keyConnectorService = new bw_KeyConnectorService(this.accountService, this.masterPasswordService, this.keyService, this.apiService, this.tokenService, this.logService, this.organizationService, this.keyGenerationService, logoutCallback, this.stateProvider);
        this.twoFactorService = new bw_TwoFactorService(this.i18nService, this.platformUtilsService, this.globalStateProvider);
        const sdkClientFactory = bw_flags_flagEnabled("sdk")
            ? new bw_DefaultSdkClientFactory()
            : new bw_NoopSdkClientFactory();
        this.sdkLoadService = new bw_CliSdkLoadService();
        this.sdkService = new bw_DefaultSdkService(sdkClientFactory, this.environmentService, this.platformUtilsService, this.accountService, this.kdfConfigService, this.keyService, customUserAgent);
        this.passwordStrengthService = new bw_PasswordStrengthService();
        this.passwordGenerationService = bw_legacyPasswordGenerationServiceFactory(this.encryptService, this.keyService, this.policyService, this.accountService, this.stateProvider);
        this.authRequestService = new bw_AuthRequestService(this.appIdService, this.accountService, this.masterPasswordService, this.keyService, this.encryptService, this.apiService, this.stateProvider);
        this.billingAccountProfileStateService = new bw_DefaultBillingAccountProfileStateService(this.stateProvider, this.platformUtilsService, this.apiService);
        this.taskSchedulerService = new bw_DefaultTaskSchedulerService(this.logService);
        this.devicesApiService = new bw_DevicesApiServiceImplementation(this.apiService);
        this.deviceTrustService = new bw_DeviceTrustService(this.keyGenerationService, this.cryptoFunctionService, this.keyService, this.encryptService, this.appIdService, this.devicesApiService, this.i18nService, this.platformUtilsService, this.stateProvider, this.secureStorageService, this.userDecryptionOptionsService, this.logService, this.configService);
        this.loginStrategyService = new bw_LoginStrategyService(this.accountService, this.masterPasswordService, this.keyService, this.apiService, this.tokenService, this.appIdService, this.platformUtilsService, this.messagingService, this.logService, this.keyConnectorService, this.environmentService, this.stateService, this.twoFactorService, this.i18nService, this.encryptService, this.passwordStrengthService, this.policyService, this.deviceTrustService, this.authRequestService, this.userDecryptionOptionsService, this.globalStateProvider, this.billingAccountProfileStateService, this.vaultTimeoutSettingsService, this.kdfConfigService, this.taskSchedulerService);
        // FIXME: CLI does not support autofill
        this.autofillSettingsService = new bw_AutofillSettingsService(this.stateProvider, this.policyService);
        this.cipherService = new bw_CipherService(this.keyService, this.domainSettingsService, this.apiService, this.i18nService, this.searchService, this.stateService, this.autofillSettingsService, this.encryptService, new bw_FallbackBulkEncryptService(this.encryptService), this.cipherFileUploadService, this.configService, this.stateProvider, this.accountService);
        this.folderService = new bw_FolderService(this.keyService, this.encryptService, this.i18nService, this.cipherService, this.stateProvider);
        this.folderApiService = new bw_FolderApiService(this.folderService, this.apiService);
        const lockedCallback = (userId) => bw_service_container_awaiter(this, void 0, void 0, function* () { return yield this.keyService.clearStoredUserKey(bw_KeySuffixOptions.Auto); });
        this.userVerificationApiService = new bw_UserVerificationApiService(this.apiService);
        this.userVerificationService = new bw_UserVerificationService(this.keyService, this.accountService, this.masterPasswordService, this.i18nService, this.userVerificationApiService, this.userDecryptionOptionsService, this.pinService, this.kdfConfigService, new bw_CliBiometricsService());
        const biometricService = new bw_CliBiometricsService();
        this.vaultTimeoutService = new bw_VaultTimeoutService(this.accountService, this.masterPasswordService, this.cipherService, this.folderService, this.collectionService, this.platformUtilsService, this.messagingService, this.searchService, this.stateService, this.authService, this.vaultTimeoutSettingsService, this.stateEventRunnerService, this.taskSchedulerService, this.logService, biometricService, lockedCallback, undefined);
        this.avatarService = new bw_AvatarService(this.apiService, this.stateProvider);
        this.syncService = new bw_DefaultSyncService(this.masterPasswordService, this.accountService, this.apiService, this.domainSettingsService, this.folderService, this.cipherService, this.keyService, this.collectionService, this.messagingService, this.policyService, this.sendService, this.logService, this.keyConnectorService, this.stateService, this.providerService, this.folderApiService, this.organizationService, this.sendApiService, this.userDecryptionOptionsService, this.avatarService, logoutCallback, this.billingAccountProfileStateService, this.tokenService, this.authService, this.stateProvider);
        this.totpService = new bw_TotpService(this.sdkService);
        this.importApiService = new bw_ImportApiService(this.apiService);
        this.importService = new bw_ImportService(this.cipherService, this.folderService, this.importApiService, this.i18nService, this.collectionService, this.keyService, this.encryptService, this.pinService, this.accountService, this.sdkService);
        this.individualExportService = new bw_IndividualVaultExportService(this.folderService, this.cipherService, this.pinService, this.keyService, this.encryptService, this.cryptoFunctionService, this.kdfConfigService, this.accountService);
        this.organizationExportService = new bw_OrganizationVaultExportService(this.cipherService, this.apiService, this.pinService, this.keyService, this.encryptService, this.cryptoFunctionService, this.collectionService, this.kdfConfigService, this.accountService);
        this.exportService = new bw_VaultExportService(this.individualExportService, this.organizationExportService);
        this.userAutoUnlockKeyService = new bw_UserAutoUnlockKeyService(this.keyService);
        this.auditService = new bw_AuditService(this.cryptoFunctionService, this.apiService);
        this.eventUploadService = new bw_EventUploadService(this.apiService, this.stateProvider, this.logService, this.authService, this.taskSchedulerService);
        this.eventCollectionService = new bw_EventCollectionService(this.cipherService, this.stateProvider, this.organizationService, this.eventUploadService, this.authService, this.accountService);
        this.organizationApiService = new bw_OrganizationApiService(this.apiService, this.syncService);
        this.providerApiService = new bw_ProviderApiService(this.apiService);
        this.organizationUserApiService = new bw_DefaultOrganizationUserApiService(this.apiService);
        this.cipherAuthorizationService = new bw_DefaultCipherAuthorizationService(this.collectionService, this.organizationService, this.accountService, this.configService);
        this.masterPasswordApiService = new bw_MasterPasswordApiService(this.apiService, this.logService);
    }
    logout() {
        return bw_service_container_awaiter(this, void 0, void 0, function* () {
            this.authService.logOut(() => {
                /* Do nothing */
            });
            const userId = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(bw_getUserId(this.accountService.activeAccount$));
            yield Promise.all([
                this.eventUploadService.uploadEvents(userId),
                this.keyService.clearKeys(),
                this.cipherService.clear(userId),
                this.folderService.clear(userId),
                this.collectionService.clear(userId),
            ]);
            yield this.stateEventRunnerService.handleEvent("logout", userId);
            yield this.stateService.clean();
            yield this.accountService.clean(userId);
            yield this.accountService.switchAccount(null);
            process.env.BW_SESSION = undefined;
        });
    }
    init() {
        return bw_service_container_awaiter(this, void 0, void 0, function* () {
            if (this.inited) {
                this.logService.warning("ServiceContainer.init called more than once");
                return;
            }
            yield this.sdkLoadService.loadAndInit();
            yield this.storageService.init();
            yield this.stateService.init();
            this.containerService.attachToGlobal(global);
            yield this.i18nService.init();
            this.twoFactorService.init();
            // If a user has a BW_SESSION key stored in their env (not process.env.BW_SESSION),
            // this should set the user key to unlock the vault on init.
            // TODO: ideally, we wouldn't want to do this here but instead only for commands that require the vault to be unlocked
            // as this runs on every command and could be a performance hit
            const activeAccount = yield (0,bw_external_rxjs_namespaceObject.firstValueFrom)(this.accountService.activeAccount$);
            if (activeAccount === null || activeAccount === void 0 ? void 0 : activeAccount.id) {
                yield this.userAutoUnlockKeyService.setUserKeyInMemoryIfAutoUserKeySet(activeAccount.id);
            }
            this.inited = true;
        });
    }
}

;// ../../bitwarden_license/bit-cli/src/service-container.ts
// FIXME: Update this file to be type safe and remove this and next line
// @ts-strict-ignore


/**
 * Instantiates services and makes them available for dependency injection.
 * Any Bitwarden-licensed services should be registered here.
 */
class bw_ServiceContainer extends bw_service_container_ServiceContainer {
    constructor() {
        super();
        this.organizationAuthRequestApiService = new bw_OrganizationAuthRequestApiService(this.apiService);
        this.organizationAuthRequestService = new bw_OrganizationAuthRequestService(this.organizationAuthRequestApiService, this.keyService, this.encryptService, this.organizationUserApiService);
    }
}

;// ../../bitwarden_license/bit-cli/src/bw.ts
var bw_bw_awaiter = (undefined && undefined.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};






function bw_main() {
    return bw_bw_awaiter(this, void 0, void 0, function* () {
        const serviceContainer = new bw_ServiceContainer();
        yield serviceContainer.init();
        yield bw_registerOssPrograms(serviceContainer);
        yield bw_registerBitPrograms(serviceContainer);
        const serveConfigurator = new bw_BitServeConfigurator(serviceContainer);
        new bw_ServeProgram(serviceContainer, serveConfigurator).register();
        bw_external_commander_namespaceObject.program.parse(process.argv);
    });
}
// Node does not support top-level await statements until ES2022, esnext, etc which we don't use yet
// eslint-disable-next-line @typescript-eslint/no-floating-promises
bw_main();

/******/ })()
;
//# sourceMappingURL=bw.js.map