import React, {useCallback, useMemo, useState} from 'react';
import {jwtDecode} from 'jwt-decode';
import {tokenManager} from '@config/tokens';
import {TokenPayload} from '@modules/login/interfaces';
import {useInstance} from '@redux/selectors';
import {
  LocalStorageKeys,
  getItemFromStorage,
  setItemFromStorage,
} from '@services/localStorage';
import {MS_PER_MINUTE} from '@shared/constants';

import DocumentsPasswordDialog, {
  DocumentsPasswordDialogProps,
} from '../components/DocumentsPasswordDialog';

const saveDocumentAccess = () =>
  setItemFromStorage({
    key: LocalStorageKeys.LAST_DOCUMENT_ACCESS_TIMESTAMP_KEY,
    value: new Date().getTime().toString(),
  });

export const useAskForPassword = () => {
  const [dialogProps, setDialogProps] =
    useState<Nullable<Omit<DocumentsPasswordDialogProps, 'showDialog'>>>(null);
  const {loginSso} = jwtDecode<TokenPayload>(
    tokenManager.getAccessToken() || '',
  );
  const {passwordInDocumentsTimer, forceOTP} = useInstance();

  const onCloseDialog = () => {
    setDialogProps(null);
  };

  const askForPassword = useCallback(
    async (callback: () => void, onClose?: () => void) => {
      const lastTimestamp = await getItemFromStorage({
        key: LocalStorageKeys.LAST_DOCUMENT_ACCESS_TIMESTAMP_KEY,
      });
      const hasDocumentsPassword =
        typeof passwordInDocumentsTimer === 'number' && !loginSso && !forceOTP;
      if (
        hasDocumentsPassword &&
        (!lastTimestamp ||
          new Date().getTime() - parseInt(lastTimestamp, 10) >=
            passwordInDocumentsTimer * MS_PER_MINUTE)
      ) {
        setDialogProps({
          onSuccess: () => {
            saveDocumentAccess();
            callback();
          },
          onCloseDialog: () => {
            onCloseDialog();
            onClose?.();
          },
        });
      } else {
        hasDocumentsPassword && saveDocumentAccess();
        callback();
      }
    },
    [loginSso, passwordInDocumentsTimer, forceOTP],
  );

  const PasswordDialog = useMemo(
    () => (
      <DocumentsPasswordDialog
        showDialog={dialogProps !== null}
        onCloseDialog={onCloseDialog}
        {...dialogProps}
      />
    ),
    [dialogProps],
  );

  return {askForPassword, PasswordDialog};
};
