diff --git a/frontend/packages/console-app/src/actions/creators/hpa-factory.ts b/frontend/packages/console-app/src/actions/creators/hpa-factory.ts index 5ce95f4d1c3..83fa37b106f 100644 --- a/frontend/packages/console-app/src/actions/creators/hpa-factory.ts +++ b/frontend/packages/console-app/src/actions/creators/hpa-factory.ts @@ -1,6 +1,7 @@ import { useMemo } from 'react'; import i18next from 'i18next'; import { Action } from '@console/dynamic-plugin-sdk'; +import { useOverlay } from '@console/dynamic-plugin-sdk/src/app/modal-support/useOverlay'; import { useK8sWatchResources } from '@console/internal/components/utils/k8s-watch-hook'; import { HorizontalPodAutoscalerModel } from '@console/internal/models'; import { @@ -14,84 +15,23 @@ import { ClusterServiceVersionModel, ClusterServiceVersionKind, } from '@console/operator-lifecycle-manager'; -import deleteHPAModal from '@console/shared/src/components/hpa/DeleteHPAModal'; +import { LazyDeleteHPAModalOverlay } from '@console/shared/src/components/hpa'; import { isHelmResource } from '@console/shared/src/utils/helm-utils'; import { doesHpaMatch } from '@console/shared/src/utils/hpa-utils'; import { isOperatorBackedService } from '@console/shared/src/utils/operator-utils'; -import { ResourceActionFactory } from './types'; const hpaRoute = ( { metadata: { name = '', namespace = '' } = {} }: K8sResourceCommon, kind: K8sKind, ) => `/workload-hpa/ns/${namespace}/${referenceForModel(kind)}/${name}`; -export const HpaActionFactory: ResourceActionFactory = { - AddHorizontalPodAutoScaler: (kind: K8sKind, obj: K8sResourceKind) => ({ - id: 'add-hpa', - label: i18next.t('console-app~Add HorizontalPodAutoscaler'), - cta: { href: hpaRoute(obj, kind) }, - insertBefore: 'add-pdb', - accessReview: { - group: HorizontalPodAutoscalerModel.apiGroup, - resource: HorizontalPodAutoscalerModel.plural, - namespace: obj.metadata?.namespace, - verb: 'create', - }, - }), - EditHorizontalPodAutoScaler: (kind: K8sKind, obj: K8sResourceCommon) => ({ - id: 'edit-hpa', - label: i18next.t('console-app~Edit HorizontalPodAutoscaler'), - cta: { href: hpaRoute(obj, kind) }, - insertBefore: 'add-pdb', - accessReview: { - group: HorizontalPodAutoscalerModel.apiGroup, - resource: HorizontalPodAutoscalerModel.plural, - namespace: obj.metadata?.namespace, - verb: 'update', - }, - }), - DeleteHorizontalPodAutoScaler: ( - kind: K8sKind, - obj: K8sResourceCommon, - relatedHPA: HorizontalPodAutoscalerKind, - ) => ({ - id: 'delete-hpa', - label: i18next.t('console-app~Remove HorizontalPodAutoscaler'), - insertBefore: 'delete-pdb', - cta: () => { - deleteHPAModal({ - workload: obj, - hpa: relatedHPA, - }); - }, - accessReview: { - group: HorizontalPodAutoscalerModel.apiGroup, - resource: HorizontalPodAutoscalerModel.plural, - namespace: obj.metadata?.namespace, - verb: 'delete', - }, - }), -}; - -export const getHpaActions = ( - kind: K8sKind, - obj: K8sResourceKind, - relatedHPAs: K8sResourceKind[], -): Action[] => { - if (relatedHPAs.length === 0) return [HpaActionFactory.AddHorizontalPodAutoScaler(kind, obj)]; - - return [ - HpaActionFactory.EditHorizontalPodAutoScaler(kind, obj), - HpaActionFactory.DeleteHorizontalPodAutoScaler(kind, obj, relatedHPAs[0]), - ]; -}; - type DeploymentActionExtraResources = { hpas: HorizontalPodAutoscalerKind[]; csvs: ClusterServiceVersionKind[]; }; export const useHPAActions = (kindObj: K8sKind, resource: K8sResourceKind) => { + const launchModal = useOverlay(); const namespace = resource?.metadata?.namespace; const watchedResources = useMemo( @@ -123,9 +63,61 @@ export const useHPAActions = (kindObj: K8sKind, resource: K8sResourceKind) => { [extraResources.csvs.data, resource], ); + const actions = useMemo(() => { + if (!supportsHPA) return []; + + if (relatedHPAs.length === 0) { + return [ + { + id: 'add-hpa', + label: i18next.t('console-app~Add HorizontalPodAutoscaler'), + cta: { href: hpaRoute(resource, kindObj) }, + insertBefore: 'add-pdb', + accessReview: { + group: HorizontalPodAutoscalerModel.apiGroup, + resource: HorizontalPodAutoscalerModel.plural, + namespace: resource.metadata?.namespace, + verb: 'create', + }, + }, + ]; + } + return [ + { + id: 'edit-hpa', + label: i18next.t('console-app~Edit HorizontalPodAutoscaler'), + cta: { href: hpaRoute(resource, kindObj) }, + insertBefore: 'add-pdb', + accessReview: { + group: HorizontalPodAutoscalerModel.apiGroup, + resource: HorizontalPodAutoscalerModel.plural, + namespace: resource.metadata?.namespace, + verb: 'update', + }, + }, + { + id: 'delete-hpa', + label: i18next.t('console-app~Remove HorizontalPodAutoscaler'), + insertBefore: 'delete-pdb', + cta: () => { + launchModal(LazyDeleteHPAModalOverlay, { + workload: resource, + hpa: relatedHPAs[0], + }); + }, + accessReview: { + group: HorizontalPodAutoscalerModel.apiGroup, + resource: HorizontalPodAutoscalerModel.plural, + namespace: resource.metadata?.namespace, + verb: 'delete', + }, + }, + ]; + }, [kindObj, launchModal, relatedHPAs, resource, supportsHPA]); + const result = useMemo<[Action[], HorizontalPodAutoscalerKind[]]>(() => { - return [supportsHPA ? getHpaActions(kindObj, resource, relatedHPAs) : [], relatedHPAs]; - }, [kindObj, relatedHPAs, resource, supportsHPA]); + return [actions, relatedHPAs]; + }, [actions, relatedHPAs]); return result; }; diff --git a/frontend/packages/console-app/src/components/console-operator/ConsoleOperatorConfig.tsx b/frontend/packages/console-app/src/components/console-operator/ConsoleOperatorConfig.tsx index a152aed5bf2..f97c48f6ddc 100644 --- a/frontend/packages/console-app/src/components/console-operator/ConsoleOperatorConfig.tsx +++ b/frontend/packages/console-app/src/components/console-operator/ConsoleOperatorConfig.tsx @@ -19,6 +19,7 @@ import { useSelector } from 'react-redux'; import { Link } from 'react-router-dom'; import { useLocation } from 'react-router-dom-v5-compat'; import { useAccessReview, WatchK8sResource } from '@console/dynamic-plugin-sdk'; +import { useOverlay } from '@console/dynamic-plugin-sdk/src/app/modal-support/useOverlay'; import { getGroupVersionKindForModel, getReferenceForModel, @@ -43,7 +44,7 @@ import { import { RootState } from '@console/internal/redux'; import { usePluginInfo } from '@console/plugin-sdk/src/api/usePluginInfo'; import PaneBody from '@console/shared/src/components/layout/PaneBody'; -import { consolePluginModal } from '@console/shared/src/components/modals/ConsolePluginModal'; +import { LazyConsolePluginModalOverlay } from '@console/shared/src/components/modals'; import { GreenCheckCircleIcon, YellowExclamationTriangleIcon, @@ -113,6 +114,7 @@ export const ConsolePluginEnabledStatus: FC = ( enabled, }) => { const { t } = useTranslation('console-app'); + const launchModal = useOverlay(); const { consoleOperatorConfig, @@ -132,7 +134,7 @@ export const ConsolePluginEnabledStatus: FC = ( type="button" isInline onClick={() => - consolePluginModal({ + launchModal(LazyConsolePluginModalOverlay, { consoleOperatorConfig, pluginName, trusted: false, diff --git a/frontend/packages/console-shared/src/components/hpa/DeleteHPAModal.tsx b/frontend/packages/console-shared/src/components/hpa/DeleteHPAModal.tsx index a343b0a5d6f..b1d02c0c514 100644 --- a/frontend/packages/console-shared/src/components/hpa/DeleteHPAModal.tsx +++ b/frontend/packages/console-shared/src/components/hpa/DeleteHPAModal.tsx @@ -4,12 +4,13 @@ import { Form } from '@patternfly/react-core'; import { ExclamationTriangleIcon } from '@patternfly/react-icons/dist/esm/icons/exclamation-triangle-icon'; import { t_global_icon_color_status_warning_default as warningColor } from '@patternfly/react-tokens'; import { useTranslation } from 'react-i18next'; +import { OverlayComponent } from '@console/dynamic-plugin-sdk/src/app/modal-support/OverlayProvider'; import { - createModalLauncher, ModalBody, ModalComponentProps, ModalSubmitFooter, ModalTitle, + ModalWrapper, } from '@console/internal/components/factory/modal'; import { LoadingInline } from '@console/internal/components/utils/status-box'; import { HorizontalPodAutoscalerModel } from '@console/internal/models'; @@ -19,12 +20,7 @@ import { K8sResourceCommon, } from '@console/internal/module/k8s'; -type DeleteHPAModalProps = ModalComponentProps & { - hpa: HorizontalPodAutoscalerKind; - workload: K8sResourceCommon; -}; - -const DeleteHPAModal: FC = ({ close, hpa, workload }) => { +const DeleteHPAModal: FC = ({ close, cancel, hpa, workload }) => { const [submitError, setSubmitError] = useState(null); const [isSubmitting, setIsSubmitting] = useState(false); const { t } = useTranslation(); @@ -82,11 +78,27 @@ const DeleteHPAModal: FC = ({ close, hpa, workload }) => { submitText={t('console-shared~Remove')} submitDanger submitDisabled={!!submitError} - cancel={close} + cancel={cancel} /> ); }; -export default createModalLauncher(DeleteHPAModal); +export const DeleteHPAModalOverlay: OverlayComponent = (props) => { + return ( + + + + ); +}; + +type DeleteHPAModalProps = ModalComponentProps & { + hpa: HorizontalPodAutoscalerKind; + workload: K8sResourceCommon; +}; diff --git a/frontend/packages/console-shared/src/components/hpa/index.ts b/frontend/packages/console-shared/src/components/hpa/index.ts index fc131d9b545..43a3b40d153 100644 --- a/frontend/packages/console-shared/src/components/hpa/index.ts +++ b/frontend/packages/console-shared/src/components/hpa/index.ts @@ -1 +1,10 @@ -export { default as deleteHPAModal } from './DeleteHPAModal'; +import { lazy } from 'react'; + +export { DeleteHPAModalOverlay } from './DeleteHPAModal'; + +// Lazy-loaded OverlayComponent for DeleteHPAModal +export const LazyDeleteHPAModalOverlay = lazy(() => + import('./DeleteHPAModal' /* webpackChunkName: "delete-hpa-modal" */).then((m) => ({ + default: m.DeleteHPAModalOverlay, + })), +); diff --git a/frontend/packages/console-shared/src/components/modals/ConsolePluginModal.tsx b/frontend/packages/console-shared/src/components/modals/ConsolePluginModal.tsx index 8a4d1306c69..f9f1225a226 100644 --- a/frontend/packages/console-shared/src/components/modals/ConsolePluginModal.tsx +++ b/frontend/packages/console-shared/src/components/modals/ConsolePluginModal.tsx @@ -1,11 +1,12 @@ import { useState } from 'react'; -import { Form } from '@patternfly/react-core'; import { useTranslation } from 'react-i18next'; +import { OverlayComponent } from '@console/dynamic-plugin-sdk/src/app/modal-support/OverlayProvider'; import { - createModalLauncher, ModalTitle, ModalBody, ModalSubmitFooter, + ModalWrapper, + ModalComponentProps, } from '@console/internal/components/factory/modal'; import { ConsoleOperatorConfigModel } from '@console/internal/models'; import { k8sPatch, K8sResourceKind } from '@console/internal/module/k8s'; @@ -48,19 +49,17 @@ export const ConsolePluginModal = (props: ConsolePluginModalProps) => { 'console-shared~This console plugin provides a custom interface that can be included in the console. Updating the enablement of this console plugin will prompt for the console to be refreshed once it has been updated. Make sure you trust this console plugin before enabling.', )}

-
- - - + + { ); }; -export const consolePluginModal = createModalLauncher(ConsolePluginModal); +export const ConsolePluginModalOverlay: OverlayComponent = (props) => { + return ( + + + + ); +}; export type ConsolePluginModalProps = { consoleOperatorConfig: K8sResourceKind; csvPluginsCount?: number; pluginName: string; trusted: boolean; - cancel?: () => void; - close?: () => void; -}; +} & ModalComponentProps; diff --git a/frontend/packages/console-shared/src/components/modals/index.ts b/frontend/packages/console-shared/src/components/modals/index.ts index ac902b242de..af77262eb3d 100644 --- a/frontend/packages/console-shared/src/components/modals/index.ts +++ b/frontend/packages/console-shared/src/components/modals/index.ts @@ -1,6 +1,15 @@ +import { lazy } from 'react'; + +// Lazy-loaded OverlayComponent for ConsolePluginModal +export const LazyConsolePluginModalOverlay = lazy(() => + import('./ConsolePluginModal' /* webpackChunkName: "console-plugin-modal" */).then((m) => ({ + default: m.ConsolePluginModalOverlay, + })), +); + export const consolePluginModal = (props) => import('./ConsolePluginModal' /* webpackChunkName: "shared-modals" */).then((m) => - m.consolePluginModal(props), + m.ConsolePluginModalOverlay(props), ); export const deleteResourceModal = (props) => diff --git a/frontend/packages/operator-lifecycle-manager/src/components/clusterserviceversion.tsx b/frontend/packages/operator-lifecycle-manager/src/components/clusterserviceversion.tsx index 4657eca88f4..73598429b05 100644 --- a/frontend/packages/operator-lifecycle-manager/src/components/clusterserviceversion.tsx +++ b/frontend/packages/operator-lifecycle-manager/src/components/clusterserviceversion.tsx @@ -30,6 +30,7 @@ import { useAccessReviewAllowed, useAccessReview, } from '@console/dynamic-plugin-sdk'; +import { useOverlay } from '@console/dynamic-plugin-sdk/src/app/modal-support/useOverlay'; import { getGroupVersionKindForModel } from '@console/dynamic-plugin-sdk/src/lib-core'; import { Conditions, ConditionTypes } from '@console/internal/components/conditions'; import { ResourceEventStream } from '@console/internal/components/events'; @@ -77,7 +78,7 @@ import { DocumentTitle } from '@console/shared/src/components/document-title/Doc import { withFallback } from '@console/shared/src/components/error'; import PaneBody from '@console/shared/src/components/layout/PaneBody'; import { ExternalLink } from '@console/shared/src/components/links/ExternalLink'; -import { consolePluginModal } from '@console/shared/src/components/modals'; +import { LazyConsolePluginModalOverlay } from '@console/shared/src/components/modals'; import { RedExclamationCircleIcon } from '@console/shared/src/components/status/icons'; import { CONSOLE_OPERATOR_CONFIG_NAME } from '@console/shared/src/constants'; import { useActiveNamespace } from '@console/shared/src/hooks/redux-selectors'; @@ -246,6 +247,7 @@ const ConsolePlugins: FC = ({ csvPlugins, trusted }) => { }; const [consoleOperatorConfig] = useK8sWatchResource(console); const { t } = useTranslation(); + const launchModal = useOverlay(); const [canPatchConsoleOperatorConfig] = useAccessReview({ group: ConsoleOperatorConfigModel.apiGroup, resource: ConsoleOperatorConfigModel.plural, @@ -273,8 +275,9 @@ const ConsolePlugins: FC = ({ csvPlugins, trusted }) => { type="button" isInline onClick={() => - consolePluginModal({ + launchModal(LazyConsolePluginModalOverlay, { consoleOperatorConfig, + csvPluginsCount, pluginName, trusted, })