UNPKG

@keycloakify/keycloak-admin-ui

Version:
286 lines 17.3 kB
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime"; import { useAlerts, useFetch } from "../ui-shared"; import { AlertVariant, Button, ButtonVariant, DataList, DragDrop, DropdownItem, Droppable, Label, PageSection, ToggleGroup, ToggleGroupItem, Toolbar, ToolbarContent, ToolbarItem, } from "@patternfly/react-core"; import { DomainIcon, TableIcon } from "@patternfly/react-icons"; import { useState } from "react"; import { Trans, useTranslation } from "react-i18next"; import { useNavigate, useParams } from "react-router-dom"; import { useAdminClient } from "../admin-client"; import { useConfirmDialog } from "../components/confirm-dialog/ConfirmDialog"; import { ViewHeader } from "../components/view-header/ViewHeader"; import { useRealm } from "../context/realm-context/RealmContext"; import useToggle from "../utils/useToggle"; import { BindFlowDialog } from "../authentication/BindFlowDialog"; import { BuildInLabel } from "../authentication/BuildInLabel"; import { DuplicateFlowModal } from "../authentication/DuplicateFlowModal"; import { EditFlowModal } from "../authentication/EditFlowModal"; import { EmptyExecutionState } from "../authentication/EmptyExecutionState"; import { FlowDiagram } from "../authentication/components/FlowDiagram"; import { FlowHeader } from "../authentication/components/FlowHeader"; import { FlowRow } from "../authentication/components/FlowRow"; import { AddStepModal } from "../authentication/components/modals/AddStepModal"; import { AddSubFlowModal } from "../authentication/components/modals/AddSubFlowModal"; import { ExecutionList, } from "../authentication/execution-model"; import { toAuthentication } from "../authentication/routes/Authentication"; import { toFlow } from "../authentication/routes/Flow"; export const providerConditionFilter = (value) => { var _a; return (_a = value.displayName) === null || _a === void 0 ? void 0 : _a.startsWith("Condition "); }; export default function FlowDetails() { const { adminClient } = useAdminClient(); const { t } = useTranslation(); const { realm } = useRealm(); const { addAlert, addError } = useAlerts(); const { id, usedBy, builtIn } = useParams(); const navigate = useNavigate(); const [key, setKey] = useState(0); const refresh = () => setKey(new Date().getTime()); const [tableView, setTableView] = useState(true); const [flow, setFlow] = useState(); const [executionList, setExecutionList] = useState(); const [liveText, setLiveText] = useState(""); const [showAddExecutionDialog, setShowAddExecutionDialog] = useState(); const [showAddSubFlowDialog, setShowSubFlowDialog] = useState(); const [selectedExecution, setSelectedExecution] = useState(); const [open, toggleOpen, setOpen] = useToggle(); const [edit, setEdit] = useState(false); const [bindFlowOpen, toggleBindFlow] = useToggle(); useFetch(async () => { const flows = await adminClient.authenticationManagement.getFlows(); const flow = flows.find((f) => f.id === id); if (!flow) { throw new Error(t("notFound")); } const executions = await adminClient.authenticationManagement.getExecutions({ flow: flow.alias, }); return { flow, executions }; }, ({ flow, executions }) => { setFlow(flow); setExecutionList(new ExecutionList(executions)); }, [key]); const executeChange = async (ex, change) => { var _a, _b, _c; try { let id = ex.id; if ("parent" in change) { let config = {}; if ("authenticationConfig" in ex) { config = await adminClient.authenticationManagement.getConfig({ id: ex.authenticationConfig, }); } try { await adminClient.authenticationManagement.delExecution({ id }); } catch (_d) { // skipping already deleted execution } if ("authenticationFlow" in ex) { const executionFlow = ex; const result = await adminClient.authenticationManagement.addFlowToFlow({ flow: ((_a = change.parent) === null || _a === void 0 ? void 0 : _a.displayName) || (flow === null || flow === void 0 ? void 0 : flow.alias), alias: executionFlow.displayName, description: executionFlow.description, provider: ex.providerId, type: "basic-flow", }); id = result.id; (_b = ex.executionList) === null || _b === void 0 ? void 0 : _b.forEach((e, i) => executeChange(e, { parent: { ...ex, id: result.id }, newIndex: i, oldIndex: i, })); } else { const result = await adminClient.authenticationManagement.addExecutionToFlow({ flow: ((_c = change.parent) === null || _c === void 0 ? void 0 : _c.displayName) || (flow === null || flow === void 0 ? void 0 : flow.alias), provider: ex.providerId, }); if (config.id) { const newConfig = { id: result.id, alias: config.alias, config: config.config, }; await adminClient.authenticationManagement.createConfig(newConfig); } id = result.id; } } const times = change.newIndex - change.oldIndex; for (let index = 0; index < Math.abs(times); index++) { if (times > 0) { await adminClient.authenticationManagement.lowerPriorityExecution({ id, }); } else { await adminClient.authenticationManagement.raisePriorityExecution({ id, }); } } refresh(); addAlert(t("updateFlowSuccess"), AlertVariant.success); } catch (error) { addError("updateFlowError", error); } }; const update = async (execution) => { // eslint-disable-next-line @typescript-eslint/no-unused-vars const { executionList, isCollapsed, ...ex } = execution; try { await adminClient.authenticationManagement.updateExecution({ flow: flow === null || flow === void 0 ? void 0 : flow.alias }, ex); refresh(); addAlert(t("updateFlowSuccess"), AlertVariant.success); } catch (error) { addError("updateFlowError", error); } }; const addExecution = async (name, type) => { try { await adminClient.authenticationManagement.addExecutionToFlow({ flow: name, provider: type.id, }); refresh(); addAlert(t("updateFlowSuccess"), AlertVariant.success); } catch (error) { addError("updateFlowError", error); } }; const addFlow = async (flow, { name, description = "", type, provider }) => { try { await adminClient.authenticationManagement.addFlowToFlow({ flow, alias: name, description, provider, type, }); refresh(); addAlert(t("updateFlowSuccess"), AlertVariant.success); } catch (error) { addError("updateFlowError", error); } }; const [toggleDeleteDialog, DeleteConfirm] = useConfirmDialog({ titleKey: "deleteConfirmExecution", children: (_jsxs(Trans, { i18nKey: "deleteConfirmExecutionMessage", children: [" ", _jsx("strong", { children: { name: selectedExecution === null || selectedExecution === void 0 ? void 0 : selectedExecution.displayName } }), "."] })), continueButtonLabel: "delete", continueButtonVariant: ButtonVariant.danger, onConfirm: async () => { try { await adminClient.authenticationManagement.delExecution({ id: selectedExecution === null || selectedExecution === void 0 ? void 0 : selectedExecution.id, }); addAlert(t("deleteExecutionSuccess"), AlertVariant.success); refresh(); } catch (error) { addError("deleteExecutionError", error); } }, }); const [toggleDeleteFlow, DeleteFlowConfirm] = useConfirmDialog({ titleKey: "deleteConfirmFlow", children: (_jsxs(Trans, { i18nKey: "deleteConfirmFlowMessage", children: [" ", _jsx("strong", { children: { flow: (flow === null || flow === void 0 ? void 0 : flow.alias) || "" } }), "."] })), continueButtonLabel: "delete", continueButtonVariant: ButtonVariant.danger, onConfirm: async () => { try { await adminClient.authenticationManagement.deleteFlow({ flowId: flow.id, }); navigate(toAuthentication({ realm })); addAlert(t("deleteFlowSuccess"), AlertVariant.success); } catch (error) { addError("deleteFlowError", error); } }, }); const hasExecutions = (executionList === null || executionList === void 0 ? void 0 : executionList.expandableList.length) !== 0; const dropdownItems = [ ...(usedBy !== "DEFAULT" ? [ _jsx(DropdownItem, { "data-testid": "set-as-default", onClick: toggleBindFlow, children: t("bindFlow") }, "default"), ] : []), _jsx(DropdownItem, { onClick: () => setOpen(true), children: t("duplicate") }, "duplicate"), ...(!builtIn ? [ _jsx(DropdownItem, { "data-testid": "edit-flow", onClick: () => setEdit(true), children: t("editInfo") }, "edit"), _jsx(DropdownItem, { "data-testid": "delete-flow", onClick: () => toggleDeleteFlow(), children: t("delete") }, "delete"), ] : []), ]; return (_jsxs(_Fragment, { children: [bindFlowOpen && (_jsx(BindFlowDialog, { flowAlias: flow === null || flow === void 0 ? void 0 : flow.alias, onClose: (usedBy) => { toggleBindFlow(); navigate(toFlow({ realm, id: id, usedBy: usedBy ? "DEFAULT" : "notInUse", builtIn: builtIn ? "builtIn" : undefined, })); } })), open && (_jsx(DuplicateFlowModal, { name: flow === null || flow === void 0 ? void 0 : flow.alias, description: flow === null || flow === void 0 ? void 0 : flow.description, toggleDialog: toggleOpen, onComplete: () => { refresh(); setOpen(false); } })), edit && (_jsx(EditFlowModal, { flow: flow, toggleDialog: () => { setEdit(!edit); refresh(); } })), _jsx(DeleteFlowConfirm, {}), _jsx(ViewHeader, { titleKey: (flow === null || flow === void 0 ? void 0 : flow.alias) || "", badges: [ { text: _jsx(Label, { children: t(`used.${usedBy}`) }) }, builtIn ? { text: _jsx(BuildInLabel, {}), id: "builtIn", } : {}, ], dropdownItems: dropdownItems }), _jsxs(PageSection, { variant: "light", children: [executionList && hasExecutions && (_jsxs(_Fragment, { children: [_jsx(Toolbar, { id: "toolbar", children: _jsxs(ToolbarContent, { children: [_jsx(ToolbarItem, { children: _jsxs(ToggleGroup, { children: [_jsx(ToggleGroupItem, { icon: _jsx(TableIcon, {}), "aria-label": t("tableView"), buttonId: "tableView", isSelected: tableView, onChange: () => setTableView(true) }), _jsx(ToggleGroupItem, { icon: _jsx(DomainIcon, {}), "aria-label": t("diagramView"), buttonId: "diagramView", isSelected: !tableView, onChange: () => setTableView(false) })] }) }), _jsx(ToolbarItem, { children: _jsx(Button, { "data-testid": "addStep", variant: "secondary", onClick: () => setShowAddExecutionDialog(true), children: t("addStep") }) }), _jsx(ToolbarItem, { children: _jsx(Button, { "data-testid": "addSubFlow", variant: "secondary", onClick: () => setShowSubFlowDialog(true), children: t("addSubFlow") }) })] }) }), _jsx(DeleteConfirm, {}), tableView && (_jsx(DragDrop, { onDrag: ({ index }) => { const item = executionList.findExecution(index); setLiveText(t("onDragStart", { item: item.displayName })); if (!item.isCollapsed) { item.isCollapsed = true; setExecutionList(executionList.clone()); } return true; }, onDragMove: ({ index }) => { const dragged = executionList.findExecution(index); setLiveText(t("onDragMove", { item: dragged === null || dragged === void 0 ? void 0 : dragged.displayName })); }, onDrop: (source, dest) => { if (dest) { const dragged = executionList.findExecution(source.index); const order = executionList.order().map((ex) => ex.id); setLiveText(t("onDragFinish", { list: dragged.displayName })); const [removed] = order.splice(source.index, 1); order.splice(dest.index, 0, removed); const change = executionList.getChange(dragged, order); executeChange(dragged, change); return true; } else { setLiveText(t("onDragCancel")); return false; } }, children: _jsx(Droppable, { hasNoWrapper: true, children: _jsxs(DataList, { "aria-label": t("flows"), children: [_jsx(FlowHeader, {}), _jsx(_Fragment, { children: executionList.expandableList.map((execution) => (_jsx(FlowRow, { builtIn: !!builtIn, execution: execution, onRowClick: (execution) => { execution.isCollapsed = !execution.isCollapsed; setExecutionList(executionList.clone()); }, onRowChange: update, onAddExecution: (execution, type) => addExecution(execution.displayName, type), onAddFlow: (execution, flow) => addFlow(execution.displayName, flow), onDelete: (execution) => { setSelectedExecution(execution); toggleDeleteDialog(); } }, execution.id))) })] }) }) })), flow && (_jsxs(_Fragment, { children: [showAddExecutionDialog && (_jsx(AddStepModal, { name: flow.alias, type: flow.providerId === "client-flow" ? "client" : "basic", onSelect: (type) => { if (type) { addExecution(flow.alias, type); } setShowAddExecutionDialog(false); } })), showAddSubFlowDialog && (_jsx(AddSubFlowModal, { name: flow.alias, onCancel: () => setShowSubFlowDialog(false), onConfirm: (newFlow) => { addFlow(flow.alias, newFlow); setShowSubFlowDialog(false); } }))] })), _jsx("div", { className: "pf-v5-screen-reader", "aria-live": "assertive", children: liveText })] })), !tableView && (executionList === null || executionList === void 0 ? void 0 : executionList.expandableList) && (_jsx(FlowDiagram, { executionList: executionList })), !(executionList === null || executionList === void 0 ? void 0 : executionList.expandableList) || (flow && !hasExecutions && (_jsx(EmptyExecutionState, { flow: flow, onAddExecution: (type) => addExecution(flow.alias, type), onAddFlow: (newFlow) => addFlow(flow.alias, newFlow) })))] })] })); } //# sourceMappingURL=FlowDetails.js.map