Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -186,18 +186,6 @@ describe('NavigationMenu', () => {
})
})

it('should render private routes with connectedRdiInstanceId', () => {
;(appContextSelector as jest.Mock).mockImplementation(() => ({
...appContextSelector,
workspace: 'redisDataIntegration',
}))

render(<NavigationMenu />)

expect(screen.getByTestId('pipeline-status-page-btn')).toBeTruthy()
expect(screen.getByTestId('pipeline-management-page-btn')).toBeTruthy()
})

describe('feature flags tests', () => {
it('should show feature dependent items when feature flag is on', async () => {
const initialStoreState = set(
Expand Down
57 changes: 0 additions & 57 deletions redisinsight/ui/src/components/navigation-menu/NavigationMenu.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,8 @@ import React from 'react'
import { FeatureFlags } from 'uiSrc/constants'
import { EXTERNAL_LINKS } from 'uiSrc/constants/links'

import { renderOnboardingTourWithChild } from 'uiSrc/utils/onboarding'
import { FeatureFlagComponent } from 'uiSrc/components'

import { RiBadge } from 'uiSrc/components/base/display/badge/RiBadge'
import {
SideBar,
SideBarContainer,
Expand All @@ -29,63 +27,11 @@ import styles from './styles.module.scss'

const NavigationMenu = () => {
const {
privateRdiRoutes,
isRdiWorkspace,
publicRoutes,
getAdditionPropsForHighlighting,
highlightedPages,
connectedRdiInstanceId,
} = useNavigation()

const renderNavItem = (nav: INavigations) => {
const fragment = (
<React.Fragment key={nav.tooltipText}>
{renderOnboardingTourWithChild(
<HighlightedFeature
{...getAdditionPropsForHighlighting(nav.pageName)}
key={nav.tooltipText}
isHighlight={!!highlightedPages[nav.pageName]?.length}
dotClassName={styles.highlightDot}
tooltipPosition="right"
transformOnHover
>
<div className={styles.navigationButtonWrapper}>
<SideBarItem
isActive={nav.isActivePage}
onClick={nav.onClick}
tooltipProps={{ text: nav.tooltipText, placement: 'right' }}
>
<SideBarItemIcon
icon={nav.iconType}
aria-label={nav.ariaLabel}
data-testid={nav.dataTestId}
/>
</SideBarItem>
{nav.isBeta && (
<RiBadge className={styles.betaLabel} label="BETA" />
)}
</div>
</HighlightedFeature>,
{ options: nav.onboard },
nav.isActivePage,
`ob-${nav.tooltipText}`,
)}
</React.Fragment>
)

return nav.featureFlag ? (
<FeatureFlagComponent
name={nav.featureFlag}
key={nav.tooltipText}
enabledByDefault
>
{fragment}
</FeatureFlagComponent>
) : (
fragment
)
}

const renderPublicNavItem = (nav: INavigations) => {
const fragment = (
<HighlightedFeature
Expand Down Expand Up @@ -131,9 +77,6 @@ const NavigationMenu = () => {
>
<SideBarContainer>
<RedisLogo isRdiWorkspace={isRdiWorkspace} />
{connectedRdiInstanceId &&
isRdiWorkspace &&
privateRdiRoutes.map(renderNavItem)}
</SideBarContainer>
<SideBarFooter className={styles.footer}>
<FeatureFlagComponent name={FeatureFlags.envDependent} enabledByDefault>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@ import {
StyledAppNavigation,
StyledAppNavigationContainer,
} from './AppNavigation.styles'
import { useNavigation } from '../hooks/useNavigation'
import FeatureFlagComponent from 'uiSrc/components/feature-flag-component/FeatureFlagComponent'
import { FeatureFlags } from 'uiSrc/constants'
import { OnboardingTourOptions } from 'uiSrc/components/onboarding-tour'
import NavigationTabTrigger from './AppNavigationTabTrigger'
import { INavigations } from 'uiSrc/components/navigation-menu/navigation.types'

type AppNavigationContainerProps = {
children?: ReactNode
Expand Down Expand Up @@ -41,18 +41,18 @@ const AppNavigationContainer = ({
)

export type AppNavigationProps = {
routes: INavigations[]
actions?: ReactNode
onChange?: (tabValue: string) => void
}

const AppNavigation = ({ actions, onChange }: AppNavigationProps) => {
const { privateRoutes } = useNavigation()
const activeTab = privateRoutes.find((route) => route.isActivePage)
const AppNavigation = ({ actions, onChange, routes }: AppNavigationProps) => {
const activeTab = routes.find((route) => route.isActivePage)
const navTabs: (TabInfo & {
isActivePage: boolean
featureFlag?: FeatureFlags
onboard?: OnboardingTourOptions
})[] = privateRoutes.map((route) => ({
})[] = routes.map((route) => ({
label: route.tooltipText,
content: '',
value: route.pageName,
Expand All @@ -73,7 +73,7 @@ const AppNavigation = ({ actions, onChange }: AppNavigationProps) => {
<Tabs.Compose
value={activeTab?.pageName}
onChange={(tabValue) => {
const tabNavItem = privateRoutes.find(
const tabNavItem = routes.find(
(route) => route.pageName === tabValue,
)
if (tabNavItem) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -147,16 +147,7 @@

const privateRdiRoutes: INavigations[] = [
{
tooltipText: 'Pipeline Status',
pageName: PageNames.rdiStatistics,
ariaLabel: 'Pipeline Status page button',
onClick: () => handleGoPage(Pages.rdiStatistics(connectedRdiInstanceId)),
dataTestId: 'pipeline-status-page-btn',
isActivePage: activePage === `/${PageNames.rdiStatistics}`,
iconType: PipelineStatisticsIcon,
},
{
tooltipText: 'Pipeline Management',
tooltipText: 'Pipeline',
pageName: PageNames.rdiPipelineManagement,
ariaLabel: 'Pipeline Management page button',
onClick: () =>
Expand All @@ -165,6 +156,15 @@
isActivePage: isPipelineManagementPath(),
iconType: PipelineManagementIcon,
},
{
tooltipText: 'Analytics',
pageName: PageNames.rdiStatistics,
ariaLabel: 'Pipeline Status page button',
onClick: () => handleGoPage(Pages.rdiStatistics(connectedRdiInstanceId)),

Check warning on line 163 in redisinsight/ui/src/components/navigation-menu/hooks/useNavigation.ts

View workflow job for this annotation

GitHub Actions / Coverage annotations (🧪 jest-coverage-report-action)

🧾 Statement is not covered

Warning! Not covered statement

Check warning on line 163 in redisinsight/ui/src/components/navigation-menu/hooks/useNavigation.ts

View workflow job for this annotation

GitHub Actions / Coverage annotations (🧪 jest-coverage-report-action)

🕹️ Function is not covered

Warning! Not covered function
dataTestId: 'pipeline-status-page-btn',
isActivePage: activePage === `/${PageNames.rdiStatistics}`,
iconType: PipelineStatisticsIcon,
},
]

const publicRoutes: INavigations[] = [
Expand Down
68 changes: 67 additions & 1 deletion redisinsight/ui/src/pages/rdi/instance/InstancePage.spec.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,13 @@ import React from 'react'
import reactRouterDom, { BrowserRouter } from 'react-router-dom'
import { instance, mock } from 'ts-mockito'

import { act, cleanup, mockedStore, render } from 'uiSrc/utils/test-utils'
import {
act,
cleanup,
mockedStore,
render,
userEvent,
} from 'uiSrc/utils/test-utils'
import { resetKeys, resetPatternKeysData } from 'uiSrc/slices/browser/keys'
import { setMonitorInitialState } from 'uiSrc/slices/cli/monitor'
import { setInitialPubSubState } from 'uiSrc/slices/pubsub/pubsub'
Expand Down Expand Up @@ -203,6 +209,35 @@ describe('InstancePage', () => {
)
})

it('should navigate to rdi pipeline management page via clicking on navigation', async () => {
const pushMock = jest.fn()
reactRouterDom.useHistory = jest.fn().mockReturnValue({
push: pushMock,
block: jest.fn(() => jest.fn()),
})

reactRouterDom.useLocation = jest
.fn()
.mockReturnValue({ pathname: Pages.rdiStatistics(RDI_INSTANCE_ID_MOCK) })

const { getByRole } = render(
<BrowserRouter>
<InstancePage {...instance(mockedProps)} />
</BrowserRouter>,
)
expect(pushMock).not.toHaveBeenCalledWith(
Pages.rdiPipelineManagement(RDI_INSTANCE_ID_MOCK),
)
const analyticsTab = getByRole('tab', { name: 'Analytics' })
expect(analyticsTab).toBeInTheDocument()

await userEvent.click(analyticsTab)

expect(pushMock).not.toHaveBeenCalledWith(
Pages.rdiPipelineManagement(RDI_INSTANCE_ID_MOCK),
)
})

it('should redirect to rdi pipeline statistics page', async () => {
;(appContextSelector as jest.Mock).mockReturnValue({
contextRdiInstanceId: RDI_INSTANCE_ID_MOCK,
Expand Down Expand Up @@ -230,4 +265,35 @@ describe('InstancePage', () => {
Pages.rdiStatistics(RDI_INSTANCE_ID_MOCK),
)
})

it('should navigate to rdi pipeline analytics page via clicking on navigation', async () => {
const pushMock = jest.fn()
reactRouterDom.useHistory = jest.fn().mockReturnValue({
push: pushMock,
block: jest.fn(() => jest.fn()),
})

reactRouterDom.useLocation = jest
.fn()
.mockReturnValue({
pathname: Pages.rdiPipelineManagement(RDI_INSTANCE_ID_MOCK),
})

const { getByRole } = render(
<BrowserRouter>
<InstancePage {...instance(mockedProps)} />
</BrowserRouter>,
)
expect(pushMock).not.toHaveBeenCalledWith(
Pages.rdiStatistics(RDI_INSTANCE_ID_MOCK),
)
const pipelineTab = getByRole('tab', { name: 'Pipeline' })
expect(pipelineTab).toBeInTheDocument()

await userEvent.click(pipelineTab)

expect(pushMock).not.toHaveBeenCalledWith(
Pages.rdiStatistics(RDI_INSTANCE_ID_MOCK),
)
})
})
16 changes: 14 additions & 2 deletions redisinsight/ui/src/pages/rdi/instance/InstancePage.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React, { useEffect } from 'react'
import React, { useEffect, useState } from 'react'
import { useDispatch, useSelector } from 'react-redux'
import { useHistory, useLocation, useParams } from 'react-router-dom'
import {
Expand All @@ -20,11 +20,13 @@ import {
} from 'uiSrc/slices/instances/instances'

import { RdiInstancePageTemplate } from 'uiSrc/templates'
import { RdiInstanceHeader } from 'uiSrc/components'
import { AppNavigation, RdiInstanceHeader } from 'uiSrc/components'
import { Col, FlexItem } from 'uiSrc/components/base/layout/flex'
import InstancePageRouter from './InstancePageRouter'
import { RdiPipelineHeader } from './components'
import styles from './styles.module.scss'
import { Nullable } from 'uiSrc/utils'
import { useNavigation } from 'uiSrc/components/navigation-menu/hooks/useNavigation'

export interface Props {
routes: IRoute[]
Expand All @@ -34,12 +36,15 @@ const RdiInstancePage = ({ routes = [] }: Props) => {
const dispatch = useDispatch()
const history = useHistory()
const { pathname } = useLocation()
const { privateRdiRoutes } = useNavigation()

const { rdiInstanceId } = useParams<{ rdiInstanceId: string }>()
const { lastPage, contextRdiInstanceId } = useSelector(appContextSelector)
const { data: rdiInstances } = useSelector(rdiInstancesSelector)
const { data: dbInstances } = useSelector(dbInstancesSelector)

const [actions, setActions] = useState<Nullable<React.ReactNode>>(null)

useEffect(() => {
if (!dbInstances?.length) {
dispatch(fetchInstancesAction())
Expand Down Expand Up @@ -80,6 +85,13 @@ const RdiInstancePage = ({ routes = [] }: Props) => {
<FlexItem>
<RdiInstanceHeader />
</FlexItem>
<FlexItem>
<AppNavigation
actions={actions}
onChange={() => setActions(null)}
routes={privateRdiRoutes}
/>
</FlexItem>
<FlexItem grow={false}>
<RdiPipelineHeader />
</FlexItem>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,16 @@ import { FlexItem, Row } from 'uiSrc/components/base/layout/flex'
import CurrentPipelineStatus from './components/current-pipeline-status'

import PipelineActions from './components/pipeline-actions'
import styles from './styles.module.scss'
import styled from 'styled-components'
import { Theme } from 'uiSrc/components/base/theme/types'

const StyledRdiPipelineHeader = styled(Row)`
padding: 0 16px;
border-bottom: 4px solid
${({ theme }: { theme: Theme }) =>
theme.components.tabs.variants.default.tabsLine.color};
height: 58px;
`

const RdiPipelineHeader = () => {
const [headerLoading, setHeaderLoading] = useState(true)
Expand Down Expand Up @@ -50,11 +59,7 @@ const RdiPipelineHeader = () => {
: undefined

return (
<Row
className={styles.wrapper}
align="center"
justify="between"
>
<StyledRdiPipelineHeader align="center" justify="between">
<FlexItem grow>
<CurrentPipelineStatus
pipelineState={pipelineState}
Expand All @@ -66,7 +71,7 @@ const RdiPipelineHeader = () => {
collectorStatus={collectorStatus}
pipelineStatus={pipelineStatus}
/>
</Row>
</StyledRdiPipelineHeader>
)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -117,14 +117,13 @@ const DeployPipelineButton = ({ loading, disabled, onReset }: Props) => {
}}
button={
<PrimaryButton
size="s"
onClick={handleClickDeploy}
icon={RiRocketIcon}
disabled={disabled}
loading={loading}
data-testid="deploy-rdi-pipeline"
>
Deploy Pipeline
Deploy
</PrimaryButton>
}
>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
import React from 'react'

import { fireEvent, render, screen, waitFor } from 'uiSrc/utils/test-utils'
import {
fireEvent,
render,
screen,
userEvent,
waitFor,
} from 'uiSrc/utils/test-utils'
import ResetPipelineButton, { PipelineButtonProps } from './ResetPipelineButton'

const mockedProps: PipelineButtonProps = {
Expand Down Expand Up @@ -46,7 +52,7 @@ describe('ResetPipelineButton', () => {
const onClick = jest.fn()
render(<ResetPipelineButton {...mockedProps} loading onClick={onClick} />)

fireEvent.click(screen.getByTestId('reset-pipeline-btn'))
userEvent.click(screen.getByTestId('reset-pipeline-btn'))
expect(onClick).not.toHaveBeenCalled()
})
})
Loading
Loading