From fefd044fa887249ba415789c49c51f0ee6a77852 Mon Sep 17 00:00:00 2001 From: Anton Standrik Date: Tue, 3 Jun 2025 13:11:40 +0300 Subject: [PATCH 01/11] feat: ai placeholders --- package-lock.json | 9 ++--- .../ComponentsProvider/componentsRegistry.ts | 6 +++- src/components/ComponentsProvider/index.ts | 3 ++ src/containers/App/App.tsx | 6 ++++ src/containers/Header/Header.tsx | 9 +++++ src/containers/Heatmap/Heatmap.tsx | 4 ++- src/containers/UserSettings/i18n/en.json | 3 ++ src/lib.ts | 1 + src/setupProxy.js | 2 ++ src/store/configureStore.ts | 35 ++++++++++++++++--- src/store/index.ts | 1 + 11 files changed, 68 insertions(+), 11 deletions(-) create mode 100644 src/components/ComponentsProvider/index.ts diff --git a/package-lock.json b/package-lock.json index cf3c52cf6..e8d169f45 100644 --- a/package-lock.json +++ b/package-lock.json @@ -21867,11 +21867,12 @@ } }, "node_modules/qs": { - "version": "6.13.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.13.1.tgz", - "integrity": "sha512-EJPeIn0CYrGu+hli1xilKAPXODtJ12T0sP63Ijx2/khC2JtuaN3JyNIpvmnkmaEtha9ocbG4A4cMcr+TvqvwQg==", + "version": "6.14.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.14.0.tgz", + "integrity": "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==", + "license": "BSD-3-Clause", "dependencies": { - "side-channel": "^1.0.6" + "side-channel": "^1.1.0" }, "engines": { "node": ">=0.6" diff --git a/src/components/ComponentsProvider/componentsRegistry.ts b/src/components/ComponentsProvider/componentsRegistry.ts index 971c37b5c..533acb4a0 100644 --- a/src/components/ComponentsProvider/componentsRegistry.ts +++ b/src/components/ComponentsProvider/componentsRegistry.ts @@ -6,11 +6,15 @@ import {StaffCard} from '../User/StaffCard'; import type {ComponentsRegistryTemplate} from './registry'; import {Registry} from './registry'; +const AnyPlaceholder = () => null; + const componentsRegistryInner = new Registry() .register('StaffCard', StaffCard) .register('AsideNavigation', AsideNavigation) .register('ErrorBoundary', ErrorBoundaryInner) - .register('ShardsTable', ShardsTable); + .register('ShardsTable', ShardsTable) + .register('AIAssistantButton', AnyPlaceholder) + .register('ChatPanel', AnyPlaceholder); export type ComponentsRegistry = ComponentsRegistryTemplate; diff --git a/src/components/ComponentsProvider/index.ts b/src/components/ComponentsProvider/index.ts new file mode 100644 index 000000000..e220c3fbd --- /dev/null +++ b/src/components/ComponentsProvider/index.ts @@ -0,0 +1,3 @@ +export {ComponentsProvider} from './ComponentsProvider'; +export {componentsRegistry} from './componentsRegistry'; +export type {ComponentsRegistry} from './componentsRegistry'; diff --git a/src/containers/App/App.tsx b/src/containers/App/App.tsx index 7c3e86731..c1f3494e5 100644 --- a/src/containers/App/App.tsx +++ b/src/containers/App/App.tsx @@ -5,6 +5,7 @@ import type {History} from 'history'; import {Helmet} from 'react-helmet-async'; import {connect} from 'react-redux'; +import {componentsRegistry} from '../../components/ComponentsProvider/componentsRegistry'; import {ErrorBoundary} from '../../components/ErrorBoundary/ErrorBoundary'; import type {RootState} from '../../store'; import {Navigation} from '../AsideNavigation/Navigation'; @@ -32,6 +33,9 @@ function App({ children, userSettings = getUserSettings({singleClusterMode}), }: AppProps) { + // Get ChatPanel from registry if it exists + const ChatPanel = componentsRegistry.get('ChatPanel'); + return ( @@ -43,6 +47,8 @@ function App({ + {/* Render ChatPanel only if it's registered */} + {ChatPanel && } ); diff --git a/src/containers/Header/Header.tsx b/src/containers/Header/Header.tsx index af0e3ef46..c26d12726 100644 --- a/src/containers/Header/Header.tsx +++ b/src/containers/Header/Header.tsx @@ -4,6 +4,7 @@ import {ArrowUpRightFromSquare, CirclePlus, PlugConnection} from '@gravity-ui/ic import {Breadcrumbs, Button, Divider, Flex, Icon} from '@gravity-ui/uikit'; import {useLocation} from 'react-router-dom'; +import {componentsRegistry} from '../../components/ComponentsProvider/componentsRegistry'; import {getConnectToDBDialog} from '../../components/ConnectToDB/ConnectToDBDialog'; import {InternalLink} from '../../components/InternalLink'; import {useAddClusterFeatureAvailable} from '../../store/reducers/capabilities/hooks'; @@ -38,6 +39,9 @@ function Header() { const isAddClusterAvailable = useAddClusterFeatureAvailable() && uiFactory.onAddCluster !== undefined; + // Get AIAssistantButton from registry if it exists + const AIAssistantButton = componentsRegistry.get('AIAssistantButton'); + const breadcrumbItems = React.useMemo(() => { let options = {...pageBreadcrumbsOptions, singleClusterMode}; @@ -76,6 +80,11 @@ function Header() { ); } + // Add AI Assistant button if component is registered + if (AIAssistantButton) { + elements.push(); + } + if (!isClustersPage && isUserAllowedToMakeChanges) { elements.push(