Skip to content

Commit

Permalink
Update unit tests
Browse files Browse the repository at this point in the history
  • Loading branch information
vanessa committed Sep 11, 2024
1 parent d980b0e commit 5276ffb
Show file tree
Hide file tree
Showing 11 changed files with 448 additions and 329 deletions.
2 changes: 1 addition & 1 deletion client/src/components/asset/AssetBoard.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React from 'react';
import * as React from 'react';
import { Grid } from '@mui/material';
import { useDispatch, useSelector } from 'react-redux';
import { GitlabInstance } from 'util/gitlab';
Expand Down
2 changes: 1 addition & 1 deletion client/src/components/asset/AssetCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -233,4 +233,4 @@ function AssetCardExecute({ asset }: AssetCardProps) {
);
}

export { AssetCardManage, AssetCardExecute };
export { AssetCardManage, AssetCardExecute, CardButtonsContainerManage, CardButtonsContainerExecute};
3 changes: 2 additions & 1 deletion client/src/route/digitaltwins/DeleteDialog.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import * as React from 'react';
import { Dispatch, SetStateAction } from 'react';
import {
Dialog,
DialogContent,
DialogActions,
Button,
Typography,
} from '@mui/material';
import React, { Dispatch, SetStateAction } from 'react';
import { useDispatch, useSelector } from 'react-redux';
import { selectDigitalTwinByName } from 'store/digitalTwin.slice';
import DigitalTwin, { formatName } from 'util/gitlabDigitalTwin';
Expand Down
2 changes: 1 addition & 1 deletion client/src/route/digitaltwins/DigitalTwinsPreview.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ export const fetchSubfolders = async (
const subfolders = await gitlabInstance.getDTSubfolders(
gitlabInstance.projectId,
);
dispatch(setAssets(subfolders)); // Dispatcha gli asset nel Redux store
dispatch(setAssets(subfolders));
} else {
dispatch(setAssets([]));
}
Expand Down
71 changes: 59 additions & 12 deletions client/test/unit/components/asset/AssetBoard.test.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
import * as React from 'react';
import { render, screen } from '@testing-library/react';
import { render, screen, fireEvent } from '@testing-library/react';
import AssetBoard from 'components/asset/AssetBoard';
import { Asset } from 'components/asset/Asset';
import { GitlabInstance } from 'util/gitlab';
import '@testing-library/jest-dom';
import store from 'store/store';
import { Provider } from 'react-redux';
import { createStore, combineReducers } from 'redux';
import assetsReducer from 'store/assets.slice';
import { Asset } from 'components/asset/Asset';
import { RootState } from 'store/store';
import { deleteAsset } from 'store/assets.slice';
import * as ReactRedux from 'react-redux';

jest.mock('react-redux', () => ({
...jest.requireActual('react-redux'),
Expand Down Expand Up @@ -37,16 +41,31 @@ jest.mock('components/asset/AssetCard', () => ({
AssetCardExecute: jest.fn(({ asset }) => (
<div>{`Execute ${asset.name}`}</div>
)),
AssetCardManage: jest.fn(({ asset }) => <div>{`Manage ${asset.name}`}</div>),
AssetCardManage: jest.fn(({ asset, onDelete }) => (
<div>
{`Manage ${asset.name}`}
<button onClick={() => onDelete()}>Delete</button>
</div>
)),
}));

const mockStore = createStore(
combineReducers({
assets: assetsReducer,
}),
{
assets: {
items: assetsMock,
},
} as RootState,
);

describe('AssetBoard', () => {
it('renders AssetCardExecute components when tab is "Execute"', () => {
render(
<Provider store={store}>
<Provider store={mockStore}>
<AssetBoard
tab="Execute"
subfolders={assetsMock}
gitlabInstance={mockGitlabInstance}
error={null}
/>
Expand All @@ -59,10 +78,9 @@ describe('AssetBoard', () => {

it('renders AssetCardManage components when tab is not "Execute"', () => {
render(
<Provider store={store}>
<Provider store={mockStore}>
<AssetBoard
tab="Manage"
subfolders={assetsMock}
gitlabInstance={mockGitlabInstance}
error={null}
/>
Expand All @@ -76,10 +94,9 @@ describe('AssetBoard', () => {
it('displays an error message when error prop is provided', () => {
const errorMessage = 'Something went wrong!';
render(
<Provider store={store}>
<Provider store={mockStore}>
<AssetBoard
tab="Manage"
subfolders={[]}
gitlabInstance={mockGitlabInstance}
error={errorMessage}
/>
Expand All @@ -90,11 +107,21 @@ describe('AssetBoard', () => {
});

it('renders correctly with no assets', () => {
const emptyStore = createStore(
combineReducers({
assets: assetsReducer,
}),
{
assets: {
items: [],
},
} as unknown as RootState,
);

render(
<Provider store={store}>
<Provider store={emptyStore}>
<AssetBoard
tab="Manage"
subfolders={[]}
gitlabInstance={mockGitlabInstance}
error={null}
/>
Expand All @@ -104,4 +131,24 @@ describe('AssetBoard', () => {
const manageCards = screen.queryAllByText(/Manage/);
expect(manageCards).toHaveLength(0);
});

it('dispatches deleteAsset action when delete button is clicked', () => {
const mockDispatch = jest.fn();
jest.spyOn(ReactRedux, 'useDispatch').mockReturnValue(mockDispatch);

render(
<Provider store={mockStore}>
<AssetBoard
tab="Manage"
gitlabInstance={mockGitlabInstance}
error={null}
/>
</Provider>,
);

const deleteButtons = screen.getAllByText('Delete');
fireEvent.click(deleteButtons[0]);

expect(mockDispatch).toHaveBeenCalledWith(deleteAsset('path1'));
});
});
200 changes: 158 additions & 42 deletions client/test/unit/components/asset/AssetCard.test.tsx
Original file line number Diff line number Diff line change
@@ -1,65 +1,181 @@
import * as React from 'react';
import { render, screen } from '@testing-library/react';
import { AssetCardManage, AssetCardExecute } from 'components/asset/AssetCard';
import { Provider } from 'react-redux';
import store from 'store/store';
import { enableFetchMocks } from 'jest-fetch-mock';
import { render, screen, fireEvent } from '@testing-library/react';
import '@testing-library/jest-dom';
import { Provider } from 'react-redux';
import { createStore, combineReducers } from 'redux';
import { AssetCardManage, AssetCardExecute, CardButtonsContainerManage, CardButtonsContainerExecute } from 'components/asset/AssetCard';
import assetsReducer from 'store/assets.slice';
import { Asset } from 'components/asset/Asset';
import { RootState } from 'store/store';
import { setDigitalTwin } from 'store/digitalTwin.slice';
import DigitalTwin from 'util/gitlabDigitalTwin';

jest.mock('route/digitaltwins/Snackbar', () => () => <div>Snackbar</div>);
jest.mock('route/digitaltwins/DetailsDialog', () => ({ showLog, setShowLog, name }: { showLog: boolean; setShowLog: (show: boolean) => void; name: string }) => (
<div>
DetailsDialog for {name}
{showLog && <button onClick={() => setShowLog(false)}>Close</button>}
</div>
));
jest.mock('route/digitaltwins/DeleteDialog', () => ({ showLog, setShowLog, name, onDelete }: { showLog: boolean; setShowLog: (show: boolean) => void; name: string; onDelete: () => void }) => (
<div>
DeleteDialog for {name}
{showLog && <button onClick={() => { setShowLog(false); onDelete(); }}>Delete</button>}
</div>
));
jest.mock('route/digitaltwins/LogDialog', () => ({ showLog, setShowLog, name }: { showLog: boolean; setShowLog: (show: boolean) => void; name: string }) => (
<div>
LogDialog for {name}
{showLog && <button onClick={() => setShowLog(false)}>Close</button>}
</div>
));

enableFetchMocks();
const assetsMock: Asset[] = [
{ name: 'Asset1', path: 'path1', description: 'Description1' },
{ name: 'Asset2', path: 'path2', description: 'Description2' },
];

interface DigitalTwinState {
[key: string]: DigitalTwin;
}

if (!AbortSignal.timeout) {
AbortSignal.timeout = (ms) => {
const controller = new AbortController();
setTimeout(() => controller.abort(new DOMException('TimeoutError')), ms);
return controller.signal;
interface SetDigitalTwinAction {
type: typeof setDigitalTwin.type;
payload: {
assetName: string;
digitalTwin: DigitalTwin;
};
}

jest.deepUnmock('components/asset/AssetCard');
type DigitalTwinActions = SetDigitalTwinAction;

jest.mock('react-redux', () => ({
...jest.requireActual('react-redux'),
}));
const mockStore = createStore(
combineReducers({
assets: assetsReducer,
digitalTwin: (state: DigitalTwinState = {}, action: DigitalTwinActions) => {
switch (action.type) {
case setDigitalTwin.type:
return { ...state, [action.payload.assetName]: action.payload.digitalTwin };
default:
return state;
}
},
}),
{
assets: { items: assetsMock },
} as RootState,
);

jest.mock('react-oidc-context', () => ({
...jest.requireActual('react-oidc-context'),
useAuth: jest.fn(),
}));
describe('AssetCard Components', () => {
it('renders AssetCard with asset and buttons', () => {
render(
<Provider store={mockStore}>
<AssetCardManage
asset={assetsMock[0]}
onDelete={() => {}}
/>
</Provider>,
);

jest.mock('util/envUtil', () => ({
...jest.requireActual('util/envUtil'),
getAuthority: jest.fn(() => 'https://example.com'),
}));
expect(screen.getByText(/Description1/)).toBeInTheDocument();
});

jest.mock('');
it('renders CardButtonsContainerManage with buttons', () => {
const setShowDetailsLog = jest.fn();
const setShowDeleteLog = jest.fn();

describe('AssetCard', () => {
const assetMock = {
name: 'TestName',
path: 'testPath',
description: 'testDescription',
};
render(
<CardButtonsContainerManage
name="Asset1"
setShowDetailsLog={setShowDetailsLog}
setShowDeleteLog={setShowDeleteLog}
/>
);

expect(screen.getByText('DetailsButton')).toBeInTheDocument();
expect(screen.getByText('ReconfigureButton')).toBeInTheDocument();
expect(screen.getByText('DeleteButton')).toBeInTheDocument();
});

it('handles button clicks in CardButtonsContainerManage', () => {
const setShowDetailsLog = jest.fn();
const setShowDeleteLog = jest.fn();

test('renders Asset Card Manage correctly', () => {
render(
<Provider store={store}>
<AssetCardManage asset={assetMock} />
);
</Provider>,
<CardButtonsContainerManage
name="Asset1"
setShowDetailsLog={setShowDetailsLog}
setShowDeleteLog={setShowDeleteLog}
/>
);

expect(screen.getByText(assetMock.name)).toBeInTheDocument();
fireEvent.click(screen.getByText('DetailsButton'));
expect(setShowDetailsLog).toHaveBeenCalled();

fireEvent.click(screen.getByText('DeleteButton'));
expect(setShowDeleteLog).toHaveBeenCalled();
});

test('renders Asset Card Execute correctly', () => {
it('renders CardButtonsContainerExecute with buttons', () => {
const setShowLog = jest.fn();

render(
<Provider store={store}>
<AssetCardExecute asset={assetMock} />
);
</Provider>,
<CardButtonsContainerExecute
assetName="Asset1"
setShowLog={setShowLog}
/>
);

expect(screen.getByText('StartStopButton')).toBeInTheDocument();
expect(screen.getByText('LogButton')).toBeInTheDocument();
});

it('handles button clicks in CardButtonsContainerExecute', () => {
const setShowLog = jest.fn();

render(
<CardButtonsContainerExecute
assetName="Asset1"
setShowLog={setShowLog}
/>
);

fireEvent.click(screen.getByText('StartStopButton'));

fireEvent.click(screen.getByText('LogButton'));
expect(setShowLog).toHaveBeenCalled();
});

it('renders AssetCardManage correctly and handles dialogs', () => {
const handleDelete = jest.fn();

render(
<Provider store={mockStore}>
<AssetCardManage
asset={assetsMock[0]}
onDelete={handleDelete}
/>
</Provider>
);

expect(screen.getByText('Snackbar')).toBeInTheDocument();
fireEvent.click(screen.getByText('DetailsDialog for Asset1'));
fireEvent.click(screen.getByText('Close'));

fireEvent.click(screen.getByText('DeleteDialog for Asset1'));
fireEvent.click(screen.getByText('Delete'));
expect(handleDelete).toHaveBeenCalled();
});

it('renders AssetCardExecute correctly and handles dialogs', () => {
render(
<Provider store={mockStore}>
<AssetCardExecute asset={assetsMock[0]} />
</Provider>
);

expect(screen.getByText(assetMock.name)).toBeInTheDocument();
expect(screen.getByText('Snackbar')).toBeInTheDocument();
fireEvent.click(screen.getByText('LogDialog for Asset1'));
fireEvent.click(screen.getByText('Close'));
});
});
Loading

0 comments on commit 5276ffb

Please sign in to comment.