All files / react-app/src/components/ConfirmationDialog userPrompt.tsx

97.14% Statements 34/35
75% Branches 9/12
100% Functions 10/10
97.05% Lines 33/34

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101                                      105x 9x       9x 9x       12x 12x       105x   105x 9x     105x   9x       105x 25x 25x   25x 9x 20x 8x 8x     12x 12x       9x     25x 2x 2x 1x   2x       25x 1x 1x 1x       25x 9x                                    
import { useEffect, useState } from "react";
 
import { ConfirmationDialog } from "@/components/ConfirmationDialog";
import { Observer } from "@/utils/basic-observable";
 
import { ButtonProps } from "../Inputs";
 
export type UserPrompt = {
  header: string;
  body: string;
  cancelButtonText?: string;
  acceptButtonText?: string;
  areButtonsReversed?: boolean;
  cancelVariant?: ButtonProps["variant"];
  onAccept: () => void;
  onCancel?: () => void;
};
 
class UserPromptObserver extends Observer<UserPrompt> {
  create = (data: UserPrompt) => {
    Iif (this.observed) {
      return;
    }
 
    this.publish(data);
    this.observed = { ...data };
  };
 
  dismiss = () => {
    this.publish(null);
    this.observed = null;
  };
}
 
const userPromptState = new UserPromptObserver();
 
const userPromptFn = (newUserPrompt: UserPrompt) => {
  return userPromptState.create(newUserPrompt);
};
 
export const userPrompt = Object.assign(userPromptFn, {
  dismiss: () => {
    userPromptState.dismiss();
  },
});
 
export const UserPrompt = () => {
  const [activeUserPrompt, setActiveUserPrompt] = useState<UserPrompt | null>(null);
  const [isOpen, setIsOpen] = useState<boolean>(false);
 
  useEffect(() => {
    const unsubscribe = userPromptState.subscribe((userPrompt) => {
      if (userPrompt) {
        setActiveUserPrompt(userPrompt);
        setIsOpen(true);
      } else {
        // artificial delay to prevent content from disappearing first
        setTimeout(() => setActiveUserPrompt(null), 100);
        setIsOpen(false);
      }
    });
 
    return unsubscribe;
  }, []);
 
  const onCancel = () => {
    Eif (activeUserPrompt) {
      if (activeUserPrompt.onCancel) {
        activeUserPrompt.onCancel();
      }
      userPromptState.dismiss();
    }
  };
 
  const onAccept = () => {
    Eif (activeUserPrompt) {
      activeUserPrompt.onAccept();
      userPromptState.dismiss();
    }
  };
 
  if (activeUserPrompt === null) {
    return null;
  }
 
  return (
    <ConfirmationDialog
      open={isOpen}
      title={activeUserPrompt.header}
      description="Dialog for user confirmation"
      body={activeUserPrompt.body}
      onAccept={onAccept}
      onCancel={onCancel}
      cancelButtonText={activeUserPrompt.cancelButtonText}
      acceptButtonText={activeUserPrompt.acceptButtonText}
      areButtonsReversed={activeUserPrompt.areButtonsReversed}
      cancelVariant={activeUserPrompt.cancelVariant}
    />
  );
};