diff --git a/assets/js/components/ChecksSelection/ChecksSelection.jsx b/assets/js/components/ChecksSelection/ChecksSelection.jsx index 86011fe1e8..27ec91f429 100644 --- a/assets/js/components/ChecksSelection/ChecksSelection.jsx +++ b/assets/js/components/ChecksSelection/ChecksSelection.jsx @@ -65,9 +65,8 @@ function ChecksSelection({ ); useEffect(() => { - onUpdateCatalog(); onClear(); - }, [onUpdateCatalog, onClear]); + }, []); const onCheckSelectionGroupChange = (checks, groupSelected) => { const groupChecks = checks.map((check) => check.id); diff --git a/assets/js/components/ChecksSelection/ChecksSelection.test.jsx b/assets/js/components/ChecksSelection/ChecksSelection.test.jsx index 6b94c78b5d..1d271330eb 100644 --- a/assets/js/components/ChecksSelection/ChecksSelection.test.jsx +++ b/assets/js/components/ChecksSelection/ChecksSelection.test.jsx @@ -51,7 +51,6 @@ describe('ChecksSelection component', () => { expect(unselectedSwitches[1]).not.toBeChecked(); expect(unselectedSwitches[2]).not.toBeChecked(); - expect(onUpdateCatalog).toBeCalled(); expect(onClear).toBeCalled(); }); @@ -93,7 +92,6 @@ describe('ChecksSelection component', () => { await user.click(offSwitches[2]); expect(screen.getAllByRole('switch')[0]).not.toBeChecked(); - expect(onUpdateCatalog).toBeCalled(); expect(onClear).toBeCalled(); }); @@ -113,7 +111,6 @@ describe('ChecksSelection component', () => { ); expect(screen.getByText(error)).toBeVisible(); - expect(onUpdateCatalog).toBeCalled(); expect(onClear).toBeCalled(); }); @@ -144,7 +141,6 @@ describe('ChecksSelection component', () => { await user.click(screen.getByText('Select Checks for Execution')); expect(onSave).toBeCalledWith([checkID1, checkID2], targetID); - expect(onUpdateCatalog).toBeCalled(); expect(onClear).toBeCalled(); }); }); diff --git a/assets/js/components/HostDetails/HostInfoBox.jsx b/assets/js/components/HostDetails/HostInfoBox.jsx new file mode 100644 index 0000000000..a5dd63ac8b --- /dev/null +++ b/assets/js/components/HostDetails/HostInfoBox.jsx @@ -0,0 +1,28 @@ +import React from 'react'; + +import ListView from '@components/ListView'; +import ProviderLabel from '@components/ProviderLabel'; + +function HostInfoBox({ provider, agentVersion }) { + return ( +
+ , + }, + { title: 'Agent version', content: agentVersion }, + { + title: '', + content: '', + }, + ]} + /> +
+ ); +} + +export default HostInfoBox; diff --git a/assets/js/components/HostDetails/HostInfoBox.test.jsx b/assets/js/components/HostDetails/HostInfoBox.test.jsx new file mode 100644 index 0000000000..cb34c0d79e --- /dev/null +++ b/assets/js/components/HostDetails/HostInfoBox.test.jsx @@ -0,0 +1,53 @@ +import React from 'react'; +import { render, screen } from '@testing-library/react'; +import '@testing-library/jest-dom'; +import HostInfoBox from './HostInfoBox'; + +describe('Host Info Box', () => { + const scenarios = [ + { + agentVersion: '1.1.0+git.dev17.1660137228.fe5ba8a', + provider: 'aws', + providerText: 'AWS', + }, + { + agentVersion: '1.2.0+git.dev17.1660137228.fe5ba8a', + provider: 'aws', + providerText: 'AWS', + }, + { + agentVersion: '2.0.0+git.dev17.1660137228.fe5ba8a', + provider: 'azure', + providerText: 'Azure', + }, + { + agentVersion: '1.1.0', + provider: 'gcp', + providerText: 'GCP', + }, + { + agentVersion: '1.2.0', + provider: 'kvm', + providerText: 'KVM', + }, + { + agentVersion: '2.0.0', + provider: 'vmware', + providerText: 'VMware', + }, + { + agentVersion: '2.1.0', + provider: 'nutanix', + providerText: 'Nutanix', + }, + ]; + + it.each(scenarios)( + 'should display host info box for $providerText', + ({ agentVersion, provider, providerText }) => { + render(); + expect(screen.getByText(providerText)).toBeTruthy(); + expect(screen.getByText(agentVersion)).toBeTruthy(); + } + ); +}); diff --git a/assets/js/components/HostDetails/index.js b/assets/js/components/HostDetails/index.js index 50233e8d07..e4b86f3ad5 100644 --- a/assets/js/components/HostDetails/index.js +++ b/assets/js/components/HostDetails/index.js @@ -1,3 +1,5 @@ import HostDetails from './HostDetails'; +import HostInfoBox from './HostInfoBox'; +export { HostInfoBox }; export default HostDetails; diff --git a/assets/js/components/HostSettings/HostSettings.jsx b/assets/js/components/HostSettings/HostSettings.jsx new file mode 100644 index 0000000000..c45a926740 --- /dev/null +++ b/assets/js/components/HostSettings/HostSettings.jsx @@ -0,0 +1,74 @@ +import React, { useEffect } from 'react'; +import { useDispatch, useSelector } from 'react-redux'; +import { useParams } from 'react-router-dom'; + +import PageHeader from '@components/PageHeader'; +import BackButton from '@components/BackButton'; +import { HostInfoBox } from '@components/HostDetails'; + +import ChecksSelection from '@components/ChecksSelection/ChecksSelection'; + +import { updateCatalog } from '@state/actions/catalog'; +import { getCatalog } from '@state/selectors/catalog'; +import { getHost } from '@state/selectors'; + +function HostSettings() { + const dispatch = useDispatch(); + + const { hostID } = useParams(); + const host = useSelector(getHost(hostID)); + + const { + data: catalog, + error: catalogError, + loading: catalogLoading, + } = useSelector(getCatalog()); + + const catalogEnv = { + provider: host?.provider, + target_type: 'host', + }; + + const onCatalogRefresh = () => { + dispatch(updateCatalog(catalogEnv)); + }; + + useEffect(() => { + if (host) { + onCatalogRefresh(); + } + }, [dispatch, host]); + + if (!host) { + return
Loading...
; + } + + return ( +
+ Back to Host Details + + Check Settings for {host?.hostname} + + + { + // TODO: dispatch check selection for a host + }} + onUpdateCatalog={onCatalogRefresh} + onClear={() => { + // TODO: + }} + saving={false} + error={null} + success={false} + /> +
+ ); +} + +export default HostSettings; diff --git a/assets/js/components/HostSettings/index.js b/assets/js/components/HostSettings/index.js new file mode 100644 index 0000000000..33ccdac03e --- /dev/null +++ b/assets/js/components/HostSettings/index.js @@ -0,0 +1,3 @@ +import HostSettings from './HostSettings'; + +export default HostSettings; diff --git a/assets/js/trento.jsx b/assets/js/trento.jsx index e08aaec7f0..5163ad2def 100644 --- a/assets/js/trento.jsx +++ b/assets/js/trento.jsx @@ -30,6 +30,7 @@ import { me } from '@lib/auth'; import { networkClient } from '@lib/network'; import Guard from '@components/Guard'; import CheckResultDetailPage from '@components/ExecutionResults/CheckResultDetail'; +import HostSettings from '@components/HostSettings'; import DatabaseDetails from './components/DatabaseDetails'; import SapSystemDetails from './components/SapSystemDetails/SapSystemDetails'; import { store } from './state'; @@ -59,6 +60,10 @@ function App() { }> } /> } /> + } + /> } /> } /> } />