From c9f2b240959edbb04823f4599f1ba3fe6d325181 Mon Sep 17 00:00:00 2001 From: Aleksandr Gumroian Date: Tue, 12 Nov 2024 17:39:01 +0100 Subject: [PATCH] Replace RebootButton with ActionButtonWithModal component and update documentation --- .../ActionButtonWithModal.js | 135 ++++++++++++++++++ .../ActionButtonWithModal.md | 39 +++++ src/common/RebootButton.js | 90 ------------ src/common/RebootButton.md | 24 ---- .../__tests__/ActionButtonWithModal.test.js | 92 ++++++++++++ src/common/__tests__/RebootButton.test.js | 63 -------- ...nap => ActionButtonWithModal.test.js.snap} | 48 ++++--- src/index.js | 2 +- styleguide.config.js | 10 +- 9 files changed, 301 insertions(+), 202 deletions(-) create mode 100644 src/common/ActionButtonWithModal/ActionButtonWithModal.js create mode 100644 src/common/ActionButtonWithModal/ActionButtonWithModal.md delete mode 100644 src/common/RebootButton.js delete mode 100644 src/common/RebootButton.md create mode 100644 src/common/__tests__/ActionButtonWithModal.test.js delete mode 100644 src/common/__tests__/RebootButton.test.js rename src/common/__tests__/__snapshots__/{RebootButton.test.js.snap => ActionButtonWithModal.test.js.snap} (74%) diff --git a/src/common/ActionButtonWithModal/ActionButtonWithModal.js b/src/common/ActionButtonWithModal/ActionButtonWithModal.js new file mode 100644 index 0000000..f500741 --- /dev/null +++ b/src/common/ActionButtonWithModal/ActionButtonWithModal.js @@ -0,0 +1,135 @@ +/* + * Copyright (C) 2019-2024 CZ.NIC z.s.p.o. (https://www.nic.cz/) + * + * This is free software, licensed under the GNU General Public License v3. + * See /LICENSE for more information. + */ + +import React, { useState, useEffect } from "react"; + +import PropTypes from "prop-types"; + +import { useAPIPost } from "../../api/hooks"; +import { API_STATE } from "../../api/utils"; +import Button from "../../bootstrap/Button"; +import { + Modal, + ModalHeader, + ModalBody, + ModalFooter, +} from "../../bootstrap/Modal"; +import { useAlert } from "../../context/alertContext/AlertContext"; + +ActionButtonWithModal.propTypes = { + /** Component that triggers the action. */ + actionTrigger: PropTypes.elementType.isRequired, + /** URL to send the action to. */ + actionUrl: PropTypes.string.isRequired, + /** Title of the modal. */ + modalTitle: PropTypes.string.isRequired, + /** Message of the modal. */ + modalMessage: PropTypes.string.isRequired, + /** Text of the action button in the modal. */ + modalActionText: PropTypes.string, + /** Props for the action button in the modal. */ + modalActionProps: PropTypes.object, + /** Message to display on successful action. */ + successMessage: PropTypes.string, + /** Message to display on failed action. */ + errorMessage: PropTypes.string, +}; + +function ActionButtonWithModal({ + actionTrigger: ActionTriggerComponent, + actionUrl, + modalTitle, + modalMessage, + modalActionText, + modalActionProps, + successMessage, + errorMessage, +}) { + const [triggered, setTriggered] = useState(false); + const [modalShown, setModalShown] = useState(false); + const [triggerActionStatus, triggerAction] = useAPIPost(actionUrl); + + const [setAlert] = useAlert(); + useEffect(() => { + if (triggerActionStatus.state === API_STATE.SUCCESS) { + setAlert( + successMessage || _("Action successful."), + API_STATE.SUCCESS + ); + } + if (triggerActionStatus.state === API_STATE.ERROR) { + setAlert(errorMessage || _("Action failed.")); + } + }, [triggerActionStatus, setAlert, successMessage, errorMessage]); + + const actionHandler = () => { + setTriggered(true); + triggerAction(); + setModalShown(false); + }; + + return ( + <> + + setModalShown(true)} + /> + + ); +} + +ActionModal.propTypes = { + shown: PropTypes.bool.isRequired, + setShown: PropTypes.func.isRequired, + onAction: PropTypes.func.isRequired, + title: PropTypes.string.isRequired, + message: PropTypes.string.isRequired, + actionText: PropTypes.string, + actionProps: PropTypes.object, +}; + +function ActionModal({ + shown, + setShown, + onAction, + title, + message, + actionText, + actionProps, +}) { + return ( + + + +

{message}

+
+ + + + +
+ ); +} + +export default ActionButtonWithModal; diff --git a/src/common/ActionButtonWithModal/ActionButtonWithModal.md b/src/common/ActionButtonWithModal/ActionButtonWithModal.md new file mode 100644 index 0000000..69c589a --- /dev/null +++ b/src/common/ActionButtonWithModal/ActionButtonWithModal.md @@ -0,0 +1,39 @@ +RebootButton component is a button that opens a modal dialog to confirm the +reboot of the device. + +## Usage + +```jsx +import React, { useEffect, createContext } from "react"; + +import Button from "../../bootstrap/Button"; +import { AlertContextProvider } from "../../context/alertContext/AlertContext"; +import ActionButtonWithModal from "./ActionButtonWithModal"; + +window.AlertContext = React.createContext(); + +const RebootButtonExample = () => { + const ActionButton = (props) => { + return ; + }; + + return ( + +