diff --git a/pkg/lib/dialogs.jsx b/pkg/lib/dialogs.jsx
index b63e861c50fc..3dd74a214239 100644
--- a/pkg/lib/dialogs.jsx
+++ b/pkg/lib/dialogs.jsx
@@ -82,6 +82,36 @@
* }
* }
*
+ * If there is a situation where you want to wait until a Dialog is closed
+ * after opening, you can "await Dialogs.show()"
+ *
+ * class Example extends React.Component {
+ * static contextType = DialogsContext;
+ *
+ * async function handleClick() {
+ * try {
+ * const result = await Dialogs.show();
+ * console.log(result);
+ * catch (err) {
+ * }
+ *
+ * }
+ *
+ * function render() {
+ * const Dialogs = this.context;
+ * return ;
+ * }
+ * }
+ *
+ * class MyDialog extends React.Component {
+ * static contextType = DialogsContext;
+ *
+ * render() {
+ *
+ *
+ * }
+ * }
+ *
*
* - Dialogs.show(component)
*
@@ -89,12 +119,19 @@
* child of the inner-most enclosing "WithDialogs" component. The
* component is of course intended to be a dialog, such as
* Patternfly's "Modal". There is only ever one of these; a second
- * call to "show" will remove the previously rendered component.
- * Passing "null" will remove the currently rendered componenet, if any.
+ * call to "show" is considered a bug and "Dialogs.close" should be called first.
+ * "Dialogs.show" returns a promise that is settled by either "Dialogs.close" or
+ * "Dialogs.reject".
+ *
+ * - Dialogs.close([args])
*
- * - Dialogs.close()
+ * Calling "Dialogs.close([args])" will close the currently open Dialog and
+ * optionally resolve the promise with the provided "args".
*
- * Same as "Dialogs.show(null)".
+ * - Dialogs.reject(err)
+ *
+ * Calling "Dialogs.reject(err)" will close the currently open Dialog
+ * and reject the promise with the provided Error.
*/
import React, { useContext, useRef, useState } from "react";
@@ -104,6 +141,8 @@ export const useDialogs = () => useContext(DialogsContext);
export const WithDialogs = ({ children }) => {
const is_open = useRef(false); // synchronous
+ const resolveRef = useRef(null);
+ const rejectRef = useRef(null);
const [dialog, setDialog] = useState(null);
const Dialogs = {
@@ -115,10 +154,28 @@ export const WithDialogs = ({ children }) => {
JSON.stringify(dialog));
is_open.current = !!component;
setDialog(component);
+ return new Promise((resolve, reject) => {
+ resolveRef.current = resolve;
+ rejectRef.current = reject;
+ });
+ },
+ close: (args) => {
+ is_open.current = false;
+ setDialog(null);
+ if (resolveRef.current !== null) {
+ resolveRef.current(args);
+ resolveRef.current = null;
+ rejectRef.current = null;
+ }
},
- close: () => {
+ reject: (err) => {
is_open.current = false;
setDialog(null);
+ if (rejectRef.current !== null) {
+ rejectRef.current(err);
+ resolveRef.current = null;
+ rejectRef.current = null;
+ }
},
isActive: () => dialog !== null
};