mirror of
https://github.com/open-metadata/OpenMetadata.git
synced 2025-08-28 19:05:53 +00:00
* feat: add list from search for test suite * feat: add list from search and owner/name filter for test suites * style: ran java linting * fix: es log failure detail * #10354 Filter test suites by owner / name * added filter logic, cypress and fixed unit test --------- Co-authored-by: Teddy Crepineau <teddy.crepineau@gmail.com>
This commit is contained in:
parent
ce18766b96
commit
073d9ea57b
@ -31,7 +31,7 @@ import {
|
|||||||
scheduleIngestion,
|
scheduleIngestion,
|
||||||
} from '../../common/Utils/Ingestion';
|
} from '../../common/Utils/Ingestion';
|
||||||
import { getToken } from '../../common/Utils/LocalStorage';
|
import { getToken } from '../../common/Utils/LocalStorage';
|
||||||
import { addOwner, removeOwner, updateOwner } from '../../common/Utils/Owner';
|
import { removeOwner, updateOwner } from '../../common/Utils/Owner';
|
||||||
import { goToServiceListingPage, Services } from '../../common/Utils/Services';
|
import { goToServiceListingPage, Services } from '../../common/Utils/Services';
|
||||||
import {
|
import {
|
||||||
DATA_QUALITY_SAMPLE_DATA_TABLE,
|
DATA_QUALITY_SAMPLE_DATA_TABLE,
|
||||||
@ -67,25 +67,11 @@ const goToProfilerTab = () => {
|
|||||||
|
|
||||||
cy.get('[data-testid="profiler"]').should('be.visible').click();
|
cy.get('[data-testid="profiler"]').should('be.visible').click();
|
||||||
};
|
};
|
||||||
const clickOnTestSuite = (testSuiteName) => {
|
|
||||||
cy.get('[data-testid="test-suite-container"]').then(($body) => {
|
const visitTestSuiteDetailsPage = (testSuiteName: string) => {
|
||||||
if ($body.find(`[data-testid="${testSuiteName}"]`).length) {
|
|
||||||
cy.get(`[data-testid="${testSuiteName}"]`).scrollIntoView().click();
|
|
||||||
} else {
|
|
||||||
if ($body.find('[data-testid="next"]').length) {
|
|
||||||
cy.get('[data-testid="next"]').click();
|
|
||||||
verifyResponseStatusCode('@testSuite', 200);
|
|
||||||
clickOnTestSuite(testSuiteName);
|
|
||||||
} else {
|
|
||||||
throw new Error('Test Suite not found');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
};
|
|
||||||
const visitTestSuiteDetailsPage = (testSuiteName) => {
|
|
||||||
interceptURL(
|
interceptURL(
|
||||||
'GET',
|
'GET',
|
||||||
'/api/v1/dataQuality/testSuites?*testSuiteType=logical*',
|
'/api/v1/dataQuality/testSuites/search/list?*testSuiteType=logical*',
|
||||||
'testSuite'
|
'testSuite'
|
||||||
);
|
);
|
||||||
interceptURL('GET', '/api/v1/dataQuality/testCases?fields=*', 'testCase');
|
interceptURL('GET', '/api/v1/dataQuality/testCases?fields=*', 'testCase');
|
||||||
@ -94,7 +80,14 @@ const visitTestSuiteDetailsPage = (testSuiteName) => {
|
|||||||
|
|
||||||
cy.get('[data-testid="by-test-suites"]').click();
|
cy.get('[data-testid="by-test-suites"]').click();
|
||||||
verifyResponseStatusCode('@testSuite', 200);
|
verifyResponseStatusCode('@testSuite', 200);
|
||||||
clickOnTestSuite(testSuiteName);
|
interceptURL(
|
||||||
|
'GET',
|
||||||
|
`/api/v1/dataQuality/testSuites/search/list?*${testSuiteName}*testSuiteType=logical*`,
|
||||||
|
'testSuiteBySearch'
|
||||||
|
);
|
||||||
|
cy.get('[data-testid="search-bar-container"]').type(testSuiteName);
|
||||||
|
verifyResponseStatusCode('@testSuiteBySearch', 200);
|
||||||
|
cy.get(`[data-testid="${testSuiteName}"]`).scrollIntoView().click();
|
||||||
};
|
};
|
||||||
|
|
||||||
const verifyFilterTestCase = () => {
|
const verifyFilterTestCase = () => {
|
||||||
@ -476,7 +469,7 @@ describe(
|
|||||||
const testCaseName = 'column_value_max_to_be_between';
|
const testCaseName = 'column_value_max_to_be_between';
|
||||||
interceptURL(
|
interceptURL(
|
||||||
'GET',
|
'GET',
|
||||||
'/api/v1/dataQuality/testSuites?*testSuiteType=logical*',
|
'/api/v1/dataQuality/testSuites/search/list?*testSuiteType=logical*',
|
||||||
'testSuite'
|
'testSuite'
|
||||||
);
|
);
|
||||||
interceptURL(
|
interceptURL(
|
||||||
@ -523,9 +516,9 @@ describe(
|
|||||||
|
|
||||||
visitTestSuiteDetailsPage(NEW_TEST_SUITE.name);
|
visitTestSuiteDetailsPage(NEW_TEST_SUITE.name);
|
||||||
|
|
||||||
addOwner(OWNER1);
|
|
||||||
updateOwner(OWNER2);
|
updateOwner(OWNER2);
|
||||||
removeOwner(OWNER2);
|
removeOwner(OWNER2);
|
||||||
|
updateOwner(OWNER1);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('Add test case to logical test suite', () => {
|
it('Add test case to logical test suite', () => {
|
||||||
@ -557,7 +550,7 @@ describe(
|
|||||||
verifyResponseStatusCode('@putTestCase', 200);
|
verifyResponseStatusCode('@putTestCase', 200);
|
||||||
});
|
});
|
||||||
|
|
||||||
it.skip('Remove test case from logical test suite', () => {
|
it('Remove test case from logical test suite', () => {
|
||||||
interceptURL('GET', '/api/v1/dataQuality/testCases?fields=*', 'testCase');
|
interceptURL('GET', '/api/v1/dataQuality/testCases?fields=*', 'testCase');
|
||||||
interceptURL(
|
interceptURL(
|
||||||
'GET',
|
'GET',
|
||||||
@ -582,7 +575,44 @@ describe(
|
|||||||
verifyResponseStatusCode('@removeTestCase', 200);
|
verifyResponseStatusCode('@removeTestCase', 200);
|
||||||
});
|
});
|
||||||
|
|
||||||
it.skip('Delete test suite', () => {
|
it('Test suite filters', () => {
|
||||||
|
interceptURL(
|
||||||
|
'GET',
|
||||||
|
'/api/v1/dataQuality/testSuites/search/list?*testSuiteType=logical*',
|
||||||
|
'testSuite'
|
||||||
|
);
|
||||||
|
interceptURL(
|
||||||
|
'GET',
|
||||||
|
'/api/v1/dataQuality/testSuites/search/list?*owner=*',
|
||||||
|
'testSuiteByOwner'
|
||||||
|
);
|
||||||
|
cy.sidebarClick(SidebarItem.DATA_QUALITY);
|
||||||
|
|
||||||
|
cy.get('[data-testid="by-test-suites"]').click();
|
||||||
|
verifyResponseStatusCode('@testSuite', 200);
|
||||||
|
|
||||||
|
// owner filter
|
||||||
|
cy.get('[data-testid="owner-select-filter"]').click();
|
||||||
|
cy.get("[data-testid='select-owner-tabs']").should('be.visible');
|
||||||
|
cy.get('.ant-tabs [id*=tab-users]').click();
|
||||||
|
|
||||||
|
interceptURL(
|
||||||
|
'GET',
|
||||||
|
`api/v1/search/query?q=*&index=user_search_index*`,
|
||||||
|
'searchOwner'
|
||||||
|
);
|
||||||
|
|
||||||
|
cy.get('[data-testid="owner-select-users-search-bar"]').type(OWNER1);
|
||||||
|
|
||||||
|
verifyResponseStatusCode('@searchOwner', 200);
|
||||||
|
cy.get(`.ant-popover [title="${OWNER1}"]`).click();
|
||||||
|
verifyResponseStatusCode('@testSuiteByOwner', 200);
|
||||||
|
cy.get(`[data-testid="${NEW_TEST_SUITE.name}"]`)
|
||||||
|
.scrollIntoView()
|
||||||
|
.should('be.visible');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('Delete test suite', () => {
|
||||||
visitTestSuiteDetailsPage(NEW_TEST_SUITE.name);
|
visitTestSuiteDetailsPage(NEW_TEST_SUITE.name);
|
||||||
|
|
||||||
cy.get('[data-testid="manage-button"]').should('be.visible').click();
|
cy.get('[data-testid="manage-button"]').should('be.visible').click();
|
||||||
@ -613,7 +643,7 @@ describe(
|
|||||||
.click();
|
.click();
|
||||||
verifyResponseStatusCode('@deleteTestSuite', 200);
|
verifyResponseStatusCode('@deleteTestSuite', 200);
|
||||||
|
|
||||||
toastNotification('Test Suite deleted successfully!');
|
toastNotification('"mysql_matrix" deleted successfully!');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('delete created service', () => {
|
it('delete created service', () => {
|
||||||
|
@ -14,4 +14,5 @@ export type DataQualitySearchParams = {
|
|||||||
searchValue: string;
|
searchValue: string;
|
||||||
status: string;
|
status: string;
|
||||||
type: string;
|
type: string;
|
||||||
|
owner: string;
|
||||||
};
|
};
|
||||||
|
@ -10,10 +10,10 @@
|
|||||||
* See the License for the specific language governing permissions and
|
* See the License for the specific language governing permissions and
|
||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
import { Button, Col, Row } from 'antd';
|
import { Button, Col, Form, Row, Select, Space } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
import { AxiosError } from 'axios';
|
import { AxiosError } from 'axios';
|
||||||
import { isString } from 'lodash';
|
import { isEmpty } from 'lodash';
|
||||||
import QueryString from 'qs';
|
import QueryString from 'qs';
|
||||||
import React, {
|
import React, {
|
||||||
ReactNode,
|
ReactNode,
|
||||||
@ -23,11 +23,18 @@ import React, {
|
|||||||
useState,
|
useState,
|
||||||
} from 'react';
|
} from 'react';
|
||||||
import { useTranslation } from 'react-i18next';
|
import { useTranslation } from 'react-i18next';
|
||||||
import { Link, useParams } from 'react-router-dom';
|
import { Link, useHistory, useLocation, useParams } from 'react-router-dom';
|
||||||
import { getEntityDetailsPath, ROUTES } from '../../../../constants/constants';
|
import {
|
||||||
|
getEntityDetailsPath,
|
||||||
|
INITIAL_PAGING_VALUE,
|
||||||
|
ROUTES,
|
||||||
|
} from '../../../../constants/constants';
|
||||||
import { PROGRESS_BAR_COLOR } from '../../../../constants/TestSuite.constant';
|
import { PROGRESS_BAR_COLOR } from '../../../../constants/TestSuite.constant';
|
||||||
import { usePermissionProvider } from '../../../../context/PermissionProvider/PermissionProvider';
|
import { usePermissionProvider } from '../../../../context/PermissionProvider/PermissionProvider';
|
||||||
import { ERROR_PLACEHOLDER_TYPE } from '../../../../enums/common.enum';
|
import {
|
||||||
|
ERROR_PLACEHOLDER_TYPE,
|
||||||
|
SORT_ORDER,
|
||||||
|
} from '../../../../enums/common.enum';
|
||||||
import { EntityTabs, EntityType } from '../../../../enums/entity.enum';
|
import { EntityTabs, EntityType } from '../../../../enums/entity.enum';
|
||||||
import { TestSummary } from '../../../../generated/entity/data/table';
|
import { TestSummary } from '../../../../generated/entity/data/table';
|
||||||
import { EntityReference } from '../../../../generated/entity/type';
|
import { EntityReference } from '../../../../generated/entity/type';
|
||||||
@ -35,8 +42,8 @@ import { TestSuite } from '../../../../generated/tests/testCase';
|
|||||||
import { usePaging } from '../../../../hooks/paging/usePaging';
|
import { usePaging } from '../../../../hooks/paging/usePaging';
|
||||||
import { DataQualityPageTabs } from '../../../../pages/DataQuality/DataQualityPage.interface';
|
import { DataQualityPageTabs } from '../../../../pages/DataQuality/DataQualityPage.interface';
|
||||||
import {
|
import {
|
||||||
getListTestSuites,
|
getListTestSuitesBySearch,
|
||||||
ListTestSuitePrams,
|
ListTestSuitePramsBySearch,
|
||||||
TestSuiteType,
|
TestSuiteType,
|
||||||
} from '../../../../rest/testAPI';
|
} from '../../../../rest/testAPI';
|
||||||
import { getEntityName } from '../../../../utils/EntityUtils';
|
import { getEntityName } from '../../../../utils/EntityUtils';
|
||||||
@ -47,14 +54,34 @@ import FilterTablePlaceHolder from '../../../common/ErrorWithPlaceholder/FilterT
|
|||||||
import NextPrevious from '../../../common/NextPrevious/NextPrevious';
|
import NextPrevious from '../../../common/NextPrevious/NextPrevious';
|
||||||
import { PagingHandlerParams } from '../../../common/NextPrevious/NextPrevious.interface';
|
import { PagingHandlerParams } from '../../../common/NextPrevious/NextPrevious.interface';
|
||||||
import { OwnerLabel } from '../../../common/OwnerLabel/OwnerLabel.component';
|
import { OwnerLabel } from '../../../common/OwnerLabel/OwnerLabel.component';
|
||||||
|
import Searchbar from '../../../common/SearchBarComponent/SearchBar.component';
|
||||||
import Table from '../../../common/Table/Table';
|
import Table from '../../../common/Table/Table';
|
||||||
|
import { UserTeamSelectableList } from '../../../common/UserTeamSelectableList/UserTeamSelectableList.component';
|
||||||
import { TableProfilerTab } from '../../../Database/Profiler/ProfilerDashboard/profilerDashboard.interface';
|
import { TableProfilerTab } from '../../../Database/Profiler/ProfilerDashboard/profilerDashboard.interface';
|
||||||
import ProfilerProgressWidget from '../../../Database/Profiler/TableProfiler/ProfilerProgressWidget/ProfilerProgressWidget';
|
import ProfilerProgressWidget from '../../../Database/Profiler/TableProfiler/ProfilerProgressWidget/ProfilerProgressWidget';
|
||||||
|
import { DataQualitySearchParams } from '../../DataQuality.interface';
|
||||||
|
|
||||||
export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
||||||
const { t } = useTranslation();
|
const { t } = useTranslation();
|
||||||
const { tab = DataQualityPageTabs.TABLES } =
|
const { tab = DataQualityPageTabs.TABLES } =
|
||||||
useParams<{ tab: DataQualityPageTabs }>();
|
useParams<{ tab: DataQualityPageTabs }>();
|
||||||
|
const history = useHistory();
|
||||||
|
const location = useLocation();
|
||||||
|
|
||||||
|
const params = useMemo(() => {
|
||||||
|
const search = location.search;
|
||||||
|
|
||||||
|
const params = QueryString.parse(
|
||||||
|
search.startsWith('?') ? search.substring(1) : search
|
||||||
|
);
|
||||||
|
|
||||||
|
return params as DataQualitySearchParams;
|
||||||
|
}, [location]);
|
||||||
|
const { searchValue, owner } = params;
|
||||||
|
const selectedOwner = useMemo(
|
||||||
|
() => (owner ? JSON.parse(owner) : undefined),
|
||||||
|
[owner]
|
||||||
|
);
|
||||||
|
|
||||||
const { permissions } = usePermissionProvider();
|
const { permissions } = usePermissionProvider();
|
||||||
const { testSuite: testSuitePermission } = permissions;
|
const { testSuite: testSuitePermission } = permissions;
|
||||||
@ -71,6 +98,14 @@ export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
|||||||
|
|
||||||
const [isLoading, setIsLoading] = useState<boolean>(true);
|
const [isLoading, setIsLoading] = useState<boolean>(true);
|
||||||
|
|
||||||
|
const ownerFilterValue = useMemo(() => {
|
||||||
|
return selectedOwner
|
||||||
|
? {
|
||||||
|
key: selectedOwner.fullyQualifiedName ?? selectedOwner.name,
|
||||||
|
label: getEntityName(selectedOwner),
|
||||||
|
}
|
||||||
|
: undefined;
|
||||||
|
}, [selectedOwner]);
|
||||||
const columns = useMemo(() => {
|
const columns = useMemo(() => {
|
||||||
const data: ColumnsType<TestSuite> = [
|
const data: ColumnsType<TestSuite> = [
|
||||||
{
|
{
|
||||||
@ -153,17 +188,27 @@ export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
|||||||
return data;
|
return data;
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
const fetchTestSuites = async (params?: ListTestSuitePrams) => {
|
const fetchTestSuites = async (
|
||||||
|
currentPage = INITIAL_PAGING_VALUE,
|
||||||
|
params?: ListTestSuitePramsBySearch
|
||||||
|
) => {
|
||||||
setIsLoading(true);
|
setIsLoading(true);
|
||||||
try {
|
try {
|
||||||
const result = await getListTestSuites({
|
const result = await getListTestSuitesBySearch({
|
||||||
...params,
|
...params,
|
||||||
fields: 'owner,summary',
|
fields: 'owner,summary',
|
||||||
includeEmptyTestSuites: !(tab === DataQualityPageTabs.TABLES),
|
q: searchValue ? `*${searchValue}*` : undefined,
|
||||||
|
owner: ownerFilterValue?.key,
|
||||||
|
offset: (currentPage - 1) * pageSize,
|
||||||
|
includeEmptyTestSuites: tab !== DataQualityPageTabs.TABLES,
|
||||||
testSuiteType:
|
testSuiteType:
|
||||||
tab === DataQualityPageTabs.TABLES
|
tab === DataQualityPageTabs.TABLES
|
||||||
? TestSuiteType.executable
|
? TestSuiteType.executable
|
||||||
: TestSuiteType.logical,
|
: TestSuiteType.logical,
|
||||||
|
sortField: 'testCaseResultSummary.timestamp',
|
||||||
|
sortType: SORT_ORDER.DESC,
|
||||||
|
sortNestedPath: 'testCaseResultSummary',
|
||||||
|
sortNestedMode: ['max'],
|
||||||
});
|
});
|
||||||
setTestSuites(result.data);
|
setTestSuites(result.data);
|
||||||
handlePagingChange(result.paging);
|
handlePagingChange(result.paging);
|
||||||
@ -175,25 +220,38 @@ export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const handleTestSuitesPageChange = useCallback(
|
const handleTestSuitesPageChange = useCallback(
|
||||||
({ cursorType, currentPage }: PagingHandlerParams) => {
|
({ currentPage }: PagingHandlerParams) => {
|
||||||
if (isString(cursorType)) {
|
fetchTestSuites(currentPage, { limit: pageSize });
|
||||||
fetchTestSuites({
|
|
||||||
[cursorType]: paging?.[cursorType],
|
|
||||||
limit: pageSize,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
handlePageChange(currentPage);
|
handlePageChange(currentPage);
|
||||||
},
|
},
|
||||||
[pageSize, paging]
|
[pageSize, paging]
|
||||||
);
|
);
|
||||||
|
|
||||||
|
const handleSearchParam = (
|
||||||
|
value: string,
|
||||||
|
key: keyof DataQualitySearchParams
|
||||||
|
) => {
|
||||||
|
history.push({
|
||||||
|
search: QueryString.stringify({
|
||||||
|
...params,
|
||||||
|
[key]: isEmpty(value) ? undefined : value,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleOwnerSelect = (owner?: EntityReference) => {
|
||||||
|
handleSearchParam(owner ? JSON.stringify(owner) : '', 'owner');
|
||||||
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (testSuitePermission?.ViewAll || testSuitePermission?.ViewBasic) {
|
if (testSuitePermission?.ViewAll || testSuitePermission?.ViewBasic) {
|
||||||
fetchTestSuites({ limit: pageSize });
|
fetchTestSuites(INITIAL_PAGING_VALUE, {
|
||||||
|
limit: pageSize,
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
setIsLoading(false);
|
setIsLoading(false);
|
||||||
}
|
}
|
||||||
}, [testSuitePermission, pageSize]);
|
}, [testSuitePermission, pageSize, searchValue, owner]);
|
||||||
|
|
||||||
if (!testSuitePermission?.ViewAll && !testSuitePermission?.ViewBasic) {
|
if (!testSuitePermission?.ViewAll && !testSuitePermission?.ViewBasic) {
|
||||||
return <ErrorPlaceHolder type={ERROR_PLACEHOLDER_TYPE.PERMISSION} />;
|
return <ErrorPlaceHolder type={ERROR_PLACEHOLDER_TYPE.PERMISSION} />;
|
||||||
@ -201,11 +259,45 @@ export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Row
|
<Row
|
||||||
className="p-x-lg p-t-md"
|
className="p-x-lg p-y-md"
|
||||||
data-testid="test-suite-container"
|
data-testid="test-suite-container"
|
||||||
gutter={[16, 16]}>
|
gutter={[16, 16]}>
|
||||||
<Col span={24}>
|
<Col span={24}>
|
||||||
<Row justify="end">
|
<Row justify="space-between">
|
||||||
|
<Col>
|
||||||
|
<Form layout="inline">
|
||||||
|
<Space
|
||||||
|
align="center"
|
||||||
|
className="w-full justify-between"
|
||||||
|
size={16}>
|
||||||
|
<Form.Item className="m-0 w-80">
|
||||||
|
<Searchbar
|
||||||
|
removeMargin
|
||||||
|
searchValue={searchValue}
|
||||||
|
onSearch={(value) =>
|
||||||
|
handleSearchParam(value, 'searchValue')
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
</Form.Item>
|
||||||
|
<Form.Item
|
||||||
|
className="m-0 w-52"
|
||||||
|
label={t('label.owner')}
|
||||||
|
name="owner">
|
||||||
|
<UserTeamSelectableList
|
||||||
|
hasPermission
|
||||||
|
owner={selectedOwner}
|
||||||
|
onUpdate={handleOwnerSelect}>
|
||||||
|
<Select
|
||||||
|
data-testid="owner-select-filter"
|
||||||
|
open={false}
|
||||||
|
placeholder={t('label.owner')}
|
||||||
|
value={ownerFilterValue}
|
||||||
|
/>
|
||||||
|
</UserTeamSelectableList>
|
||||||
|
</Form.Item>
|
||||||
|
</Space>
|
||||||
|
</Form>
|
||||||
|
</Col>
|
||||||
<Col>
|
<Col>
|
||||||
{tab === DataQualityPageTabs.TEST_SUITES &&
|
{tab === DataQualityPageTabs.TEST_SUITES &&
|
||||||
testSuitePermission?.Create && (
|
testSuitePermission?.Create && (
|
||||||
@ -239,6 +331,7 @@ export const TestSuites = ({ summaryPanel }: { summaryPanel: ReactNode }) => {
|
|||||||
<Col span={24}>
|
<Col span={24}>
|
||||||
{showPagination && (
|
{showPagination && (
|
||||||
<NextPrevious
|
<NextPrevious
|
||||||
|
isNumberBased
|
||||||
currentPage={currentPage}
|
currentPage={currentPage}
|
||||||
pageSize={pageSize}
|
pageSize={pageSize}
|
||||||
paging={paging}
|
paging={paging}
|
||||||
|
@ -14,7 +14,7 @@ import { render, screen } from '@testing-library/react';
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { MemoryRouter } from 'react-router-dom';
|
import { MemoryRouter } from 'react-router-dom';
|
||||||
import { DataQualityPageTabs } from '../../../../pages/DataQuality/DataQualityPage.interface';
|
import { DataQualityPageTabs } from '../../../../pages/DataQuality/DataQualityPage.interface';
|
||||||
import { getListTestSuites } from '../../../../rest/testAPI';
|
import { getListTestSuitesBySearch } from '../../../../rest/testAPI';
|
||||||
import { TestSuites } from './TestSuites.component';
|
import { TestSuites } from './TestSuites.component';
|
||||||
|
|
||||||
const testSuitePermission = {
|
const testSuitePermission = {
|
||||||
@ -29,6 +29,9 @@ const testSuitePermission = {
|
|||||||
const mockUseParam = { tab: DataQualityPageTabs.TABLES } as {
|
const mockUseParam = { tab: DataQualityPageTabs.TABLES } as {
|
||||||
tab?: DataQualityPageTabs;
|
tab?: DataQualityPageTabs;
|
||||||
};
|
};
|
||||||
|
const mockLocation = {
|
||||||
|
search: '',
|
||||||
|
};
|
||||||
|
|
||||||
jest.mock('../../../../context/PermissionProvider/PermissionProvider', () => ({
|
jest.mock('../../../../context/PermissionProvider/PermissionProvider', () => ({
|
||||||
usePermissionProvider: jest.fn().mockImplementation(() => ({
|
usePermissionProvider: jest.fn().mockImplementation(() => ({
|
||||||
@ -40,7 +43,7 @@ jest.mock('../../../../context/PermissionProvider/PermissionProvider', () => ({
|
|||||||
jest.mock('../../../../rest/testAPI', () => {
|
jest.mock('../../../../rest/testAPI', () => {
|
||||||
return {
|
return {
|
||||||
...jest.requireActual('../../../../rest/testAPI'),
|
...jest.requireActual('../../../../rest/testAPI'),
|
||||||
getListTestSuites: jest
|
getListTestSuitesBySearch: jest
|
||||||
.fn()
|
.fn()
|
||||||
.mockImplementation(() =>
|
.mockImplementation(() =>
|
||||||
Promise.resolve({ data: [], paging: { total: 0 } })
|
Promise.resolve({ data: [], paging: { total: 0 } })
|
||||||
@ -49,13 +52,30 @@ jest.mock('../../../../rest/testAPI', () => {
|
|||||||
});
|
});
|
||||||
jest.mock('react-router-dom', () => {
|
jest.mock('react-router-dom', () => {
|
||||||
return {
|
return {
|
||||||
...jest.requireActual('react-router-dom'),
|
Link: jest
|
||||||
|
.fn()
|
||||||
|
.mockImplementation(({ children, ...rest }) => (
|
||||||
|
<div {...rest}>{children}</div>
|
||||||
|
)),
|
||||||
|
useLocation: jest.fn().mockImplementation(() => mockLocation),
|
||||||
|
useHistory: jest.fn(),
|
||||||
useParams: jest.fn().mockImplementation(() => mockUseParam),
|
useParams: jest.fn().mockImplementation(() => mockUseParam),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
jest.mock('../../../common/NextPrevious/NextPrevious', () => {
|
jest.mock('../../../common/NextPrevious/NextPrevious', () => {
|
||||||
return jest.fn().mockImplementation(() => <div>NextPrevious.component</div>);
|
return jest.fn().mockImplementation(() => <div>NextPrevious.component</div>);
|
||||||
});
|
});
|
||||||
|
jest.mock(
|
||||||
|
'../../../common/UserTeamSelectableList/UserTeamSelectableList.component',
|
||||||
|
() => ({
|
||||||
|
UserTeamSelectableList: jest
|
||||||
|
.fn()
|
||||||
|
.mockImplementation(({ children }) => <div>{children}</div>),
|
||||||
|
})
|
||||||
|
);
|
||||||
|
jest.mock('../../../common/SearchBarComponent/SearchBar.component', () => {
|
||||||
|
return jest.fn().mockImplementation(() => <div>SearchBar.component</div>);
|
||||||
|
});
|
||||||
jest.mock('../../../common/ErrorWithPlaceholder/ErrorPlaceHolder', () => {
|
jest.mock('../../../common/ErrorWithPlaceholder/ErrorPlaceHolder', () => {
|
||||||
return jest
|
return jest
|
||||||
.fn()
|
.fn()
|
||||||
@ -84,13 +104,17 @@ describe('TestSuites component', () => {
|
|||||||
'label.owner',
|
'label.owner',
|
||||||
]);
|
]);
|
||||||
expect(await screen.findByTestId('test-suite-table')).toBeInTheDocument();
|
expect(await screen.findByTestId('test-suite-table')).toBeInTheDocument();
|
||||||
|
expect(
|
||||||
|
await screen.findByTestId('owner-select-filter')
|
||||||
|
).toBeInTheDocument();
|
||||||
|
expect(await screen.findByText('SearchBar.component')).toBeInTheDocument();
|
||||||
expect(
|
expect(
|
||||||
await screen.findByText('SummaryPanel.component')
|
await screen.findByText('SummaryPanel.component')
|
||||||
).toBeInTheDocument();
|
).toBeInTheDocument();
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should send testSuiteType executable in api, if active tab is tables', async () => {
|
it('should send testSuiteType executable in api, if active tab is tables', async () => {
|
||||||
const mockGetListTestSuites = getListTestSuites as jest.Mock;
|
const mockGetListTestSuites = getListTestSuitesBySearch as jest.Mock;
|
||||||
|
|
||||||
render(<TestSuites {...mockProps} />);
|
render(<TestSuites {...mockProps} />);
|
||||||
|
|
||||||
@ -101,12 +125,41 @@ describe('TestSuites component', () => {
|
|||||||
fields: 'owner,summary',
|
fields: 'owner,summary',
|
||||||
includeEmptyTestSuites: false,
|
includeEmptyTestSuites: false,
|
||||||
limit: 15,
|
limit: 15,
|
||||||
|
offset: 0,
|
||||||
|
owner: undefined,
|
||||||
|
q: undefined,
|
||||||
|
sortField: 'testCaseResultSummary.timestamp',
|
||||||
|
sortNestedMode: ['max'],
|
||||||
|
sortNestedPath: 'testCaseResultSummary',
|
||||||
|
sortType: 'desc',
|
||||||
|
testSuiteType: 'executable',
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('filters API call should be made, if owner is selected', async () => {
|
||||||
|
mockLocation.search =
|
||||||
|
'?owner={"id":"84c3e66f-a4a6-42ab-b85c-b578f46d3bca","type":"user","name":"admin","fullyQualifiedName":"admin"}&searchValue=sales';
|
||||||
|
testSuitePermission.ViewAll = true;
|
||||||
|
const mockGetListTestSuites = getListTestSuitesBySearch as jest.Mock;
|
||||||
|
render(<TestSuites {...mockProps} />, { wrapper: MemoryRouter });
|
||||||
|
|
||||||
|
expect(mockGetListTestSuites).toHaveBeenCalledWith({
|
||||||
|
fields: 'owner,summary',
|
||||||
|
includeEmptyTestSuites: false,
|
||||||
|
limit: 15,
|
||||||
|
offset: 0,
|
||||||
|
owner: 'admin',
|
||||||
|
q: '*sales*',
|
||||||
|
sortField: 'testCaseResultSummary.timestamp',
|
||||||
|
sortNestedMode: ['max'],
|
||||||
|
sortNestedPath: 'testCaseResultSummary',
|
||||||
|
sortType: 'desc',
|
||||||
testSuiteType: 'executable',
|
testSuiteType: 'executable',
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
it('pagination should visible if total is grater than 15', async () => {
|
it('pagination should visible if total is grater than 15', async () => {
|
||||||
(getListTestSuites as jest.Mock).mockImplementationOnce(() =>
|
(getListTestSuitesBySearch as jest.Mock).mockImplementationOnce(() =>
|
||||||
Promise.resolve({ data: [], paging: { total: 16 } })
|
Promise.resolve({ data: [], paging: { total: 16 } })
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -126,8 +179,9 @@ describe('TestSuites component', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should send testSuiteType logical in api, if active tab is tables', async () => {
|
it('should send testSuiteType logical in api, if active tab is tables', async () => {
|
||||||
|
mockLocation.search = '';
|
||||||
mockUseParam.tab = DataQualityPageTabs.TEST_SUITES;
|
mockUseParam.tab = DataQualityPageTabs.TEST_SUITES;
|
||||||
const mockGetListTestSuites = getListTestSuites as jest.Mock;
|
const mockGetListTestSuites = getListTestSuitesBySearch as jest.Mock;
|
||||||
|
|
||||||
render(<TestSuites {...mockProps} />, { wrapper: MemoryRouter });
|
render(<TestSuites {...mockProps} />, { wrapper: MemoryRouter });
|
||||||
|
|
||||||
@ -138,6 +192,13 @@ describe('TestSuites component', () => {
|
|||||||
fields: 'owner,summary',
|
fields: 'owner,summary',
|
||||||
includeEmptyTestSuites: true,
|
includeEmptyTestSuites: true,
|
||||||
limit: 15,
|
limit: 15,
|
||||||
|
offset: 0,
|
||||||
|
owner: undefined,
|
||||||
|
q: undefined,
|
||||||
|
sortField: 'testCaseResultSummary.timestamp',
|
||||||
|
sortNestedMode: ['max'],
|
||||||
|
sortNestedPath: 'testCaseResultSummary',
|
||||||
|
sortType: 'desc',
|
||||||
testSuiteType: 'logical',
|
testSuiteType: 'logical',
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -145,6 +145,7 @@ export const UserTeamSelectableList = ({
|
|||||||
id: updateItems[0].id,
|
id: updateItems[0].id,
|
||||||
type: activeTab === 'teams' ? EntityType.TEAM : EntityType.USER,
|
type: activeTab === 'teams' ? EntityType.TEAM : EntityType.USER,
|
||||||
name: updateItems[0].name,
|
name: updateItems[0].name,
|
||||||
|
fullyQualifiedName: updateItems[0].fullyQualifiedName,
|
||||||
displayName: updateItems[0].displayName,
|
displayName: updateItems[0].displayName,
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
@ -47,6 +47,15 @@ export type ListTestSuitePrams = ListParams & {
|
|||||||
testSuiteType?: TestSuiteType;
|
testSuiteType?: TestSuiteType;
|
||||||
includeEmptyTestSuites?: boolean;
|
includeEmptyTestSuites?: boolean;
|
||||||
};
|
};
|
||||||
|
export type ListTestSuitePramsBySearch = ListTestSuitePrams & {
|
||||||
|
q?: string;
|
||||||
|
sortType?: SORT_ORDER;
|
||||||
|
sortNestedMode?: string[];
|
||||||
|
sortNestedPath?: string;
|
||||||
|
sortField?: string;
|
||||||
|
owner?: string;
|
||||||
|
offset?: number;
|
||||||
|
};
|
||||||
|
|
||||||
export type ListTestCaseParams = ListParams & {
|
export type ListTestCaseParams = ListParams & {
|
||||||
entityLink?: string;
|
entityLink?: string;
|
||||||
@ -245,6 +254,19 @@ export const getListTestSuites = async (params?: ListTestSuitePrams) => {
|
|||||||
return response.data;
|
return response.data;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const getListTestSuitesBySearch = async (
|
||||||
|
params?: ListTestSuitePramsBySearch
|
||||||
|
) => {
|
||||||
|
const response = await APIClient.get<PagingResponse<TestSuite[]>>(
|
||||||
|
`${testSuiteUrl}/search/list`,
|
||||||
|
{
|
||||||
|
params,
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
return response.data;
|
||||||
|
};
|
||||||
|
|
||||||
export const createTestSuites = async (data: CreateTestSuite) => {
|
export const createTestSuites = async (data: CreateTestSuite) => {
|
||||||
const response = await APIClient.post<
|
const response = await APIClient.post<
|
||||||
CreateTestSuite,
|
CreateTestSuite,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user