Home > database >  Close modal only after API finishes
Close modal only after API finishes

Time:03-16

I am learning ReactJS.
I am showing a popup-modal to add a new account in account list through API call.

{newExpendixAccount && (
            <ConfirmDialog
              title="Create New Expendix Account"
              children={<ModalContent action="new" />}
              open={newExpendixAccount}
              setOpen={setNewExpendixAccount}
              onConfirm={newAccount}
              isLoading={false}
              onClose={() => {}}
            />
          )}

As you see in above code if newExpendixAccount === true then it will show a modal-popup like given in below image :

enter image description here

Now If I write something in input and press YES button then onConfirm={newAccount} will run.

Given below is the newAccount function :

  const newAccount = () => {
    const data = {
      PKID: 0,
      AccountName: accountInputValue.username,
    };
    createOrUpdateAccount(data, (res) => { // calling API and getting response
      if (res?.data?.Success === true && res?.status === 200) {
        NotificationManager.success(res?.data?.ErrorMessage);
        setAccountData((prevState) => ({
          ...prevState,
          usersAccountData: [...prevState.usersAccountData, res.data.Model],
        }));
        return true;
      } else {
        NotificationManager.error(res.message || res?.data?.ErrorMessage);
        return false;
      }
    });
  };

Given below is the ConfirmDialog component :

const ConfirmDialog = ({
  title,
  children,
  open,
  setOpen,
  onConfirm,
  isLoading,
  onClose,
}) => {
  return (
    <Dialog
      open={open}
      onClose={() => setOpen(false)}
      aria-labelledby='confirm-dialog'
    >
      <DialogTitle id='confirm-dialog'>{title}</DialogTitle>
      {isLoading && <LinearProgress></LinearProgress>}
      <DialogContent>{children}</DialogContent>
      <DialogActions>
        <Button
          variant='contained'
          onClick={() => {
            setOpen(false);
            onClose();
          }}
          color='secondary'
        >
          No
        </Button>
        <Button
          variant='contained'
          onClick={() => {
            setOpen(false);
            onConfirm();
          }}
          disabled={isLoading}
          color='primary'
        >
          Yes
        </Button>
      </DialogActions>
    </Dialog>
  );
};
export default ConfirmDialog;

Please take a look on method onClick of YES button :

        <Button
          variant='contained'
          onClick={() => {
            setOpen(false);
            onConfirm();
          }}
          disabled={isLoading}
          color='primary'
        >
          Yes
        </Button>

The problem is in onClick function.

Whenever I press YES button, it first closes the modal pop-up by running setOpen(false) and then it calls the API function onConfirm() which I sent as prop.

I want to close pop-up modal only after API request finishes.
How do I do this ?

CodePudding user response:

One approach I can think of is, you make the onClick() function as async, and await on onConfirm() to finish (for this you need to modify your newAccount() to return a promise which will resolve once the API call is completed)

//this is how it should look like
onClick = {
  async () => {
    await onConfirm();
    setOpen(false);
  }
}

CodePudding user response:

you can update you function to accept a function that will call it once the api call is done.

  const newAccount = (onFinish = () => {}) => {
    const data = {
      PKID: 0,
      AccountName: accountInputValue.username,
    };
    createOrUpdateAccount(data, (res) => { // calling API and getting response
      if (res?.data?.Success === true && res?.status === 200) {
        NotificationManager.success(res?.data?.ErrorMessage);
        setAccountData((prevState) => ({
          ...prevState,
          usersAccountData: [...prevState.usersAccountData, res.data.Model],
        }));
        return true;
      } else {
        NotificationManager.error(res.message || res?.data?.ErrorMessage);
        return false;
      }
      onFinish();
    });
  };

then do:

onClick={() => {
    onConfirm(() => {setOpen(false)});
}}
  • Related