Fixed #667 Add Loader to every page, wherever it's required before data renders . (#729)

* Fixed #667 Add Loader to every page, wherever it's required before data renders .

* changed service no found placeholder.
This commit is contained in:
Sachin Chaurasiya 2021-10-11 19:22:27 +05:30 committed by GitHub
parent ec51fadf19
commit 79ca909f2f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 146 additions and 111 deletions

View File

@ -27,13 +27,16 @@ import { getRecentlyViewedData } from '../../utils/CommonUtils';
import { getOwnerFromId, getTierFromTableTags } from '../../utils/TableUtils'; import { getOwnerFromId, getTierFromTableTags } from '../../utils/TableUtils';
import { getTableTags } from '../../utils/TagsUtils'; import { getTableTags } from '../../utils/TagsUtils';
import TableDataCard from '../common/table-data-card/TableDataCard'; import TableDataCard from '../common/table-data-card/TableDataCard';
import Loader from '../Loader/Loader';
import Onboarding from '../onboarding/Onboarding'; import Onboarding from '../onboarding/Onboarding';
const RecentlyViewed: FunctionComponent = () => { const RecentlyViewed: FunctionComponent = () => {
const recentlyViewedData = getRecentlyViewedData(); const recentlyViewedData = getRecentlyViewedData();
const [data, setData] = useState<Array<FormatedTableData>>([]); const [data, setData] = useState<Array<FormatedTableData>>([]);
const [isLoading, setIsloading] = useState<boolean>(false);
const fetchRecentlyViewedEntity = async () => { const fetchRecentlyViewedEntity = async () => {
setIsloading(true);
const arrData: Array<FormatedTableData> = []; const arrData: Array<FormatedTableData> = [];
for (const oData of recentlyViewedData) { for (const oData of recentlyViewedData) {
@ -156,6 +159,7 @@ const RecentlyViewed: FunctionComponent = () => {
break; break;
} }
} }
setIsloading(false);
setData(arrData); setData(arrData);
}; };
@ -166,6 +170,10 @@ const RecentlyViewed: FunctionComponent = () => {
}, []); }, []);
return ( return (
<>
{isLoading ? (
<Loader />
) : (
<> <>
{data.length ? ( {data.length ? (
data.map((item, index) => { data.map((item, index) => {
@ -190,6 +198,8 @@ const RecentlyViewed: FunctionComponent = () => {
<Onboarding /> <Onboarding />
)} )}
</> </>
)}
</>
); );
}; };

View File

@ -92,7 +92,7 @@ describe('Test SearchedData Component', () => {
} }
); );
const searchedDataContainer = getByTestId(container, 'fluid-container'); const searchedDataContainer = getByTestId(container, 'search-container');
expect(searchedDataContainer).toBeInTheDocument(); expect(searchedDataContainer).toBeInTheDocument();
}); });

View File

@ -27,7 +27,6 @@ import {
} from '../../utils/TableUtils'; } from '../../utils/TableUtils';
import ErrorPlaceHolderES from '../common/error-with-placeholder/ErrorPlaceHolderES'; import ErrorPlaceHolderES from '../common/error-with-placeholder/ErrorPlaceHolderES';
import TableDataCard from '../common/table-data-card/TableDataCard'; import TableDataCard from '../common/table-data-card/TableDataCard';
import PageContainer from '../containers/PageContainer';
import Loader from '../Loader/Loader'; import Loader from '../Loader/Loader';
import Onboarding from '../onboarding/Onboarding'; import Onboarding from '../onboarding/Onboarding';
import Pagination from '../Pagination'; import Pagination from '../Pagination';
@ -55,7 +54,6 @@ const SearchedData: React.FC<SearchedDataProp> = ({
showOnlyChildren = false, showOnlyChildren = false,
searchText, searchText,
totalValue, totalValue,
fetchLeftPanel,
}: SearchedDataProp) => { }: SearchedDataProp) => {
const highlightSearchResult = () => { const highlightSearchResult = () => {
return data.map((table, index) => { return data.map((table, index) => {
@ -108,12 +106,10 @@ const SearchedData: React.FC<SearchedDataProp> = ({
return ( return (
<> <>
<PageContainer leftPanelContent={fetchLeftPanel?.()}>
<div className="container-fluid" data-testid="fluid-container">
{isLoading ? ( {isLoading ? (
<Loader /> <Loader />
) : ( ) : (
<> <div data-testid="search-container">
{totalValue > 0 || showOnboardingTemplate || showOnlyChildren ? ( {totalValue > 0 || showOnboardingTemplate || showOnlyChildren ? (
<> <>
{children} {children}
@ -148,10 +144,8 @@ const SearchedData: React.FC<SearchedDataProp> = ({
<ErrorPlaceHolderES query={searchText} type="noData" /> <ErrorPlaceHolderES query={searchText} type="noData" />
</> </>
)} )}
</>
)}
</div> </div>
</PageContainer> )}
</> </>
); );
}; };

View File

@ -16,6 +16,7 @@
*/ */
import { ServiceTypes } from 'Models'; import { ServiceTypes } from 'Models';
import noDataFound from '../assets/img/no-data-placeholder.png';
import noService from '../assets/img/no-service.png'; import noService from '../assets/img/no-service.png';
import airflow from '../assets/img/service-icon-airflow.png'; import airflow from '../assets/img/service-icon-airflow.png';
import athena from '../assets/img/service-icon-athena.png'; import athena from '../assets/img/service-icon-athena.png';
@ -39,6 +40,7 @@ import tableau from '../assets/img/service-icon-tableau.png';
import trino from '../assets/img/service-icon-trino.png'; import trino from '../assets/img/service-icon-trino.png';
import plus from '../assets/svg/plus.svg'; import plus from '../assets/svg/plus.svg';
export const NoDataFoundPlaceHolder = noDataFound;
export const MYSQL = mysql; export const MYSQL = mysql;
export const MSSQL = mssql; export const MSSQL = mssql;
export const REDSHIFT = redshift; export const REDSHIFT = redshift;

View File

@ -54,10 +54,12 @@ describe('Test Explore page', () => {
const { container } = render(<ExplorePage />, { const { container } = render(<ExplorePage />, {
wrapper: MemoryRouter, wrapper: MemoryRouter,
}); });
const pageContainer = await findByTestId(container, 'fluid-container');
const searchData = await findByTestId(container, 'search-data'); const searchData = await findByTestId(container, 'search-data');
const wrappedContent = await findByTestId(container, 'wrapped-content'); const wrappedContent = await findByTestId(container, 'wrapped-content');
const tabs = await findAllByTestId(container, 'tab'); const tabs = await findAllByTestId(container, 'tab');
expect(pageContainer).toBeInTheDocument();
expect(searchData).toBeInTheDocument(); expect(searchData).toBeInTheDocument();
expect(wrappedContent).toBeInTheDocument(); expect(wrappedContent).toBeInTheDocument();
expect(tabs.length).toBe(4); expect(tabs.length).toBe(4);

View File

@ -32,6 +32,7 @@ import { searchData } from '../../axiosAPIs/miscAPI';
import { Button } from '../../components/buttons/Button/Button'; import { Button } from '../../components/buttons/Button/Button';
import ErrorPlaceHolderES from '../../components/common/error-with-placeholder/ErrorPlaceHolderES'; import ErrorPlaceHolderES from '../../components/common/error-with-placeholder/ErrorPlaceHolderES';
import FacetFilter from '../../components/common/facetfilter/FacetFilter'; import FacetFilter from '../../components/common/facetfilter/FacetFilter';
import PageContainer from '../../components/containers/PageContainer';
import DropDownList from '../../components/dropdown/DropDownList'; import DropDownList from '../../components/dropdown/DropDownList';
import SearchedData from '../../components/searched-data/SearchedData'; import SearchedData from '../../components/searched-data/SearchedData';
import { import {
@ -577,6 +578,7 @@ const ExplorePage: React.FC = (): React.ReactElement => {
setFieldList(tabsInfo[getCurrentTab(tab) - 1].sortingFields); setFieldList(tabsInfo[getCurrentTab(tab) - 1].sortingFields);
setSortField(tabsInfo[getCurrentTab(tab) - 1].sortField); setSortField(tabsInfo[getCurrentTab(tab) - 1].sortField);
setSortOrder('desc'); setSortOrder('desc');
setError('');
setCurrentTab(getCurrentTab(tab)); setCurrentTab(getCurrentTab(tab));
setSearchIndex(getCurrentIndex(tab)); setSearchIndex(getCurrentIndex(tab));
setCurrentPage(1); setCurrentPage(1);
@ -609,17 +611,23 @@ const ExplorePage: React.FC = (): React.ReactElement => {
const fetchLeftPanel = () => { const fetchLeftPanel = () => {
return ( return (
<>
{!error && (
<FacetFilter <FacetFilter
aggregations={getAggrWithDefaultValue(aggregations, visibleFilters)} aggregations={getAggrWithDefaultValue(aggregations, visibleFilters)}
filters={getFacetedFilter()} filters={getFacetedFilter()}
onClearFilter={(value) => onClearFilterHandler(value)} onClearFilter={(value) => onClearFilterHandler(value)}
onSelectHandler={handleSelectedFilter} onSelectHandler={handleSelectedFilter}
/> />
)}
</>
); );
}; };
return ( return (
<> <PageContainer leftPanelContent={fetchLeftPanel()}>
<div className="container-fluid" data-testid="fluid-container">
{getTabs()}
{error ? ( {error ? (
<ErrorPlaceHolderES errorMessage={error} type="error" /> <ErrorPlaceHolderES errorMessage={error} type="error" />
) : ( ) : (
@ -627,15 +635,14 @@ const ExplorePage: React.FC = (): React.ReactElement => {
showResultCount showResultCount
currentPage={currentPage} currentPage={currentPage}
data={data} data={data}
fetchLeftPanel={fetchLeftPanel}
isLoading={isLoading} isLoading={isLoading}
paginate={paginate} paginate={paginate}
searchText={searchText} searchText={searchText}
totalValue={totalNumberOfValue}> totalValue={totalNumberOfValue}
{getTabs()} />
</SearchedData>
)} )}
</> </div>
</PageContainer>
); );
}; };

View File

@ -223,11 +223,13 @@ describe('Test MyData page', () => {
const { container } = render(<MyDataPage />, { const { container } = render(<MyDataPage />, {
wrapper: MemoryRouter, wrapper: MemoryRouter,
}); });
const pageContainer = await findByTestId(container, 'fluid-container');
const searchData = await findByTestId(container, 'search-data'); const searchData = await findByTestId(container, 'search-data');
const wrappedContent = await findByTestId(container, 'wrapped-content'); const wrappedContent = await findByTestId(container, 'wrapped-content');
const tabs = await findAllByTestId(container, 'tab'); const tabs = await findAllByTestId(container, 'tab');
const myDataHeader = await findByText(container, /MyDataHeader/i); const myDataHeader = await findByText(container, /MyDataHeader/i);
expect(pageContainer).toBeInTheDocument();
expect(searchData).toBeInTheDocument(); expect(searchData).toBeInTheDocument();
expect(wrappedContent).toBeInTheDocument(); expect(wrappedContent).toBeInTheDocument();
expect(myDataHeader).toBeInTheDocument(); expect(myDataHeader).toBeInTheDocument();

View File

@ -23,6 +23,7 @@ import React, { useEffect, useRef, useState } from 'react';
import AppState from '../../AppState'; import AppState from '../../AppState';
import { searchData } from '../../axiosAPIs/miscAPI'; import { searchData } from '../../axiosAPIs/miscAPI';
import ErrorPlaceHolderES from '../../components/common/error-with-placeholder/ErrorPlaceHolderES'; import ErrorPlaceHolderES from '../../components/common/error-with-placeholder/ErrorPlaceHolderES';
import PageContainer from '../../components/containers/PageContainer';
import Loader from '../../components/Loader/Loader'; import Loader from '../../components/Loader/Loader';
import MyDataHeader from '../../components/my-data/MyDataHeader'; import MyDataHeader from '../../components/my-data/MyDataHeader';
import RecentlyViewed from '../../components/recently-viewed/RecentlyViewed'; import RecentlyViewed from '../../components/recently-viewed/RecentlyViewed';
@ -44,6 +45,7 @@ const MyDataPage: React.FC = (): React.ReactElement => {
const [currentPage, setCurrentPage] = useState<number>(1); const [currentPage, setCurrentPage] = useState<number>(1);
const [totalNumberOfValue, setTotalNumberOfValues] = useState<number>(0); const [totalNumberOfValue, setTotalNumberOfValues] = useState<number>(0);
const [isLoading, setIsLoading] = useState<boolean>(true); const [isLoading, setIsLoading] = useState<boolean>(true);
const [isEntityLoading, setIsEntityLoading] = useState<boolean>(true);
const [currentTab, setCurrentTab] = useState<number>(1); const [currentTab, setCurrentTab] = useState<number>(1);
const [error, setError] = useState<string>(''); const [error, setError] = useState<string>('');
const [filter, setFilter] = useState<string>(''); const [filter, setFilter] = useState<string>('');
@ -72,7 +74,9 @@ const MyDataPage: React.FC = (): React.ReactElement => {
}; };
const fetchTableData = (setAssetCount = false) => { const fetchTableData = (setAssetCount = false) => {
if (!isEntityLoading) {
setIsLoading(true); setIsLoading(true);
}
searchData( searchData(
'', '',
currentPage, currentPage,
@ -91,10 +95,12 @@ const MyDataPage: React.FC = (): React.ReactElement => {
setAggregations(res.data.aggregations); setAggregations(res.data.aggregations);
} }
setIsLoading(false); setIsLoading(false);
setIsEntityLoading(false);
} else { } else {
setData([]); setData([]);
setTotalNumberOfValues(0); setTotalNumberOfValues(0);
setIsLoading(false); setIsLoading(false);
setIsEntityLoading(false);
} }
}) })
.catch((err: AxiosError) => { .catch((err: AxiosError) => {
@ -104,6 +110,7 @@ const MyDataPage: React.FC = (): React.ReactElement => {
body: err.response?.data?.responseMessage ?? ERROR500, body: err.response?.data?.responseMessage ?? ERROR500,
}); });
setIsLoading(false); setIsLoading(false);
setIsEntityLoading(false);
}); });
}; };
@ -115,6 +122,7 @@ const MyDataPage: React.FC = (): React.ReactElement => {
className={`tw-pb-2 tw-px-4 tw-gh-tabs ${getActiveTabClass(1)}`} className={`tw-pb-2 tw-px-4 tw-gh-tabs ${getActiveTabClass(1)}`}
data-testid="tab" data-testid="tab"
onClick={() => { onClick={() => {
setIsEntityLoading(true);
setCurrentTab(1); setCurrentTab(1);
setFilter(''); setFilter('');
setCurrentPage(1); setCurrentPage(1);
@ -125,6 +133,7 @@ const MyDataPage: React.FC = (): React.ReactElement => {
className={`tw-pb-2 tw-px-4 tw-gh-tabs ${getActiveTabClass(2)}`} className={`tw-pb-2 tw-px-4 tw-gh-tabs ${getActiveTabClass(2)}`}
data-testid="tab" data-testid="tab"
onClick={() => { onClick={() => {
setIsEntityLoading(true);
setCurrentTab(2); setCurrentTab(2);
setFilter(Ownership.OWNER); setFilter(Ownership.OWNER);
setCurrentPage(1); setCurrentPage(1);
@ -135,6 +144,7 @@ const MyDataPage: React.FC = (): React.ReactElement => {
className={`tw-pb-2 tw-px-4 tw-gh-tabs ${getActiveTabClass(3)}`} className={`tw-pb-2 tw-px-4 tw-gh-tabs ${getActiveTabClass(3)}`}
data-testid="tab" data-testid="tab"
onClick={() => { onClick={() => {
setIsEntityLoading(true);
setCurrentTab(3); setCurrentTab(3);
setFilter(Ownership.FOLLOWERS); setFilter(Ownership.FOLLOWERS);
setCurrentPage(1); setCurrentPage(1);
@ -162,24 +172,16 @@ const MyDataPage: React.FC = (): React.ReactElement => {
}, []); }, []);
return ( return (
<>
{isLoading ? (
<Loader />
) : (
<> <>
{error ? ( {error ? (
<ErrorPlaceHolderES errorMessage={error} type="error" /> <ErrorPlaceHolderES errorMessage={error} type="error" />
) : ( ) : (
<SearchedData
showOnboardingTemplate
currentPage={currentPage}
data={data}
paginate={paginate}
searchText="*"
showOnlyChildren={currentTab === 1}
showResultCount={filter && data.length > 0 ? true : false}
totalValue={totalNumberOfValue}>
<> <>
{isLoading ? (
<Loader />
) : (
<PageContainer>
<div className="container-fluid" data-testid="fluid-container">
<MyDataHeader <MyDataHeader
countAssets={getTotalEntityCountByService( countAssets={getTotalEntityCountByService(
aggregations?.['sterms#Service']?.buckets as Bucket[] aggregations?.['sterms#Service']?.buckets as Bucket[]
@ -190,9 +192,20 @@ const MyDataPage: React.FC = (): React.ReactElement => {
)} )}
/> />
{getTabs()} {getTabs()}
<SearchedData
showOnboardingTemplate
currentPage={currentPage}
data={data}
isLoading={isEntityLoading}
paginate={paginate}
searchText="*"
showOnlyChildren={currentTab === 1}
showResultCount={filter && data.length > 0 ? true : false}
totalValue={totalNumberOfValue}>
{currentTab === 1 ? <RecentlyViewed /> : null} {currentTab === 1 ? <RecentlyViewed /> : null}
</>
</SearchedData> </SearchedData>
</div>
</PageContainer>
)} )}
</> </>
)} )}

View File

@ -44,7 +44,7 @@ import {
} from '../../constants/constants'; } from '../../constants/constants';
import { import {
arrServiceTypes, arrServiceTypes,
NOSERVICE, NoDataFoundPlaceHolder,
PLUS, PLUS,
servicesDisplayName, servicesDisplayName,
} from '../../constants/services.const'; } from '../../constants/services.const';
@ -81,7 +81,7 @@ export type ApiData = {
const ServicesPage = () => { const ServicesPage = () => {
const showToast = useToastContext(); const showToast = useToastContext();
const { isAdminUser } = useAuth(); const { isAdminUser, isAuthDisabled } = useAuth();
const [isModalOpen, setIsModalOpen] = useState(false); const [isModalOpen, setIsModalOpen] = useState(false);
const [serviceName, setServiceName] = const [serviceName, setServiceName] =
useState<ServiceTypes>('databaseServices'); useState<ServiceTypes>('databaseServices');
@ -328,6 +328,7 @@ const ServicesPage = () => {
value: service.collection.name, value: service.collection.name,
}; };
}); });
setIsLoading(false);
} else { } else {
setIsLoading(false); setIsLoading(false);
} }
@ -466,7 +467,7 @@ const ServicesPage = () => {
title={TITLE_FOR_NON_ADMIN_ACTION}> title={TITLE_FOR_NON_ADMIN_ACTION}>
<div <div
className={classNames('tw-inline-block', { className={classNames('tw-inline-block', {
'tw-opacity-40': !isAdminUser, 'tw-opacity-40': !isAdminUser && !isAuthDisabled,
})} })}
style={{ width: '100%' }}> style={{ width: '100%' }}>
<div <div
@ -484,7 +485,11 @@ const ServicesPage = () => {
) : ( ) : (
<div className="tw-flex tw-items-center tw-flex-col"> <div className="tw-flex tw-items-center tw-flex-col">
<div className="tw-mt-24"> <div className="tw-mt-24">
<img alt="No Service" src={NOSERVICE} /> <img
alt="No Service"
src={NoDataFoundPlaceHolder}
width={250}
/>
</div> </div>
<div className="tw-mt-11"> <div className="tw-mt-11">
<p className="tw-text-lg"> <p className="tw-text-lg">

View File

@ -219,12 +219,12 @@ const TagsPage = () => {
return ( return (
<> <>
{isLoading ? (
<Loader />
) : (
<PageContainer className="py-0" leftPanelContent={fetchLeftPanel()}>
{error ? ( {error ? (
<p className="tw-text-2xl tw-text-center tw-m-auto">{error}</p> <p className="tw-text-2xl tw-text-center tw-m-auto">{error}</p>
) : (
<PageContainer className="py-0" leftPanelContent={fetchLeftPanel()}>
{isLoading ? (
<Loader />
) : ( ) : (
<div className="container-fluid py-3" data-testid="tags-container"> <div className="container-fluid py-3" data-testid="tags-container">
{currentCategory && ( {currentCategory && (