123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146 |
- import { t } from "i18next";
- import { useEffect, useState } from "react";
- import {
- generateSRPClient,
- generateSRPSetupAttributes,
- } from "@ente/accounts/services/srp";
- import {
- generateAndSaveIntermediateKeyAttributes,
- generateLoginSubKey,
- saveKeyInSessionStore,
- } from "@ente/shared/crypto/helpers";
- import { LS_KEYS, getData, setData } from "@ente/shared/storage/localStorage";
- import { startSRPSetup, updateSRPAndKeys } from "@ente/accounts/api/srp";
- import SetPasswordForm, {
- SetPasswordFormProps,
- } from "@ente/accounts/components/SetPasswordForm";
- import { PAGES } from "@ente/accounts/constants/pages";
- import { UpdatedKey } from "@ente/accounts/types/user";
- import { SESSION_KEYS } from "@ente/shared/storage/sessionStorage";
- import { getActualKey } from "@ente/shared/user";
- import { KEK, KeyAttributes, User } from "@ente/shared/user/types";
- import {
- convertBase64ToBuffer,
- convertBufferToBase64,
- } from "@ente/accounts/utils";
- import { APP_HOMES } from "@ente/shared/apps/constants";
- import { PageProps } from "@ente/shared/apps/types";
- import { VerticallyCentered } from "@ente/shared/components/Container";
- import FormPaper from "@ente/shared/components/Form/FormPaper";
- import FormPaperFooter from "@ente/shared/components/Form/FormPaper/Footer";
- import FormPaperTitle from "@ente/shared/components/Form/FormPaper/Title";
- import LinkButton from "@ente/shared/components/LinkButton";
- import ComlinkCryptoWorker from "@ente/shared/crypto";
- import InMemoryStore, { MS_KEYS } from "@ente/shared/storage/InMemoryStore";
- export default function ChangePassword({ appName, router }: PageProps) {
- const [token, setToken] = useState<string>();
- const [user, setUser] = useState<User>();
- useEffect(() => {
- const user = getData(LS_KEYS.USER);
- setUser(user);
- if (!user?.token) {
- InMemoryStore.set(MS_KEYS.REDIRECT_URL, PAGES.CHANGE_PASSWORD);
- router.push(PAGES.ROOT);
- } else {
- setToken(user.token);
- }
- }, []);
- const onSubmit: SetPasswordFormProps["callback"] = async (
- passphrase,
- setFieldError,
- ) => {
- const cryptoWorker = await ComlinkCryptoWorker.getInstance();
- const key = await getActualKey();
- const keyAttributes: KeyAttributes = getData(LS_KEYS.KEY_ATTRIBUTES);
- const kekSalt = await cryptoWorker.generateSaltToDeriveKey();
- let kek: KEK;
- try {
- kek = await cryptoWorker.deriveSensitiveKey(passphrase, kekSalt);
- } catch (e) {
- setFieldError("confirm", t("PASSWORD_GENERATION_FAILED"));
- return;
- }
- const encryptedKeyAttributes = await cryptoWorker.encryptToB64(
- key,
- kek.key,
- );
- const updatedKey: UpdatedKey = {
- kekSalt,
- encryptedKey: encryptedKeyAttributes.encryptedData,
- keyDecryptionNonce: encryptedKeyAttributes.nonce,
- opsLimit: kek.opsLimit,
- memLimit: kek.memLimit,
- };
- const loginSubKey = await generateLoginSubKey(kek.key);
- const { srpUserID, srpSalt, srpVerifier } =
- await generateSRPSetupAttributes(loginSubKey);
- const srpClient = await generateSRPClient(
- srpSalt,
- srpUserID,
- loginSubKey,
- );
- const srpA = convertBufferToBase64(srpClient.computeA());
- const { setupID, srpB } = await startSRPSetup(token, {
- srpUserID,
- srpSalt,
- srpVerifier,
- srpA,
- });
- srpClient.setB(convertBase64ToBuffer(srpB));
- const srpM1 = convertBufferToBase64(srpClient.computeM1());
- await updateSRPAndKeys(token, {
- setupID,
- srpM1,
- updatedKeyAttr: updatedKey,
- });
- const updatedKeyAttributes = Object.assign(keyAttributes, updatedKey);
- await generateAndSaveIntermediateKeyAttributes(
- passphrase,
- updatedKeyAttributes,
- key,
- );
- await saveKeyInSessionStore(SESSION_KEYS.ENCRYPTION_KEY, key);
- redirectToAppHome();
- };
- const redirectToAppHome = () => {
- setData(LS_KEYS.SHOW_BACK_BUTTON, { value: true });
- router.push(APP_HOMES.get(appName));
- };
- return (
- <VerticallyCentered>
- <FormPaper>
- <FormPaperTitle>{t("CHANGE_PASSWORD")}</FormPaperTitle>
- <SetPasswordForm
- userEmail={user?.email}
- callback={onSubmit}
- buttonText={t("CHANGE_PASSWORD")}
- />
- {(getData(LS_KEYS.SHOW_BACK_BUTTON)?.value ?? true) && (
- <FormPaperFooter>
- <LinkButton onClick={router.back}>
- {t("GO_BACK")}
- </LinkButton>
- </FormPaperFooter>
- )}
- </FormPaper>
- </VerticallyCentered>
- );
- }
|