From 1786e8999c17671df9fc8b3ac2c951713657d6f9 Mon Sep 17 00:00:00 2001 From: Manojava Koushik <111366021+manojava-gk@users.noreply.github.com> Date: Fri, 26 Jan 2024 12:26:27 +0530 Subject: [PATCH] feat(company certificate): list company certificates (#437) --- CHANGELOG.md | 4 +- src/assets/locales/de/main.json | 18 ++ src/assets/locales/en/main.json | 18 ++ .../CompanyCertificate.scss | 151 ++++++++++++++++ .../CompanyCertificateCard.tsx | 70 ++++++++ .../CompanyCertificateElements.tsx | 58 +++++++ .../pages/CompanyCertificates/index.tsx | 163 ++++++++++++++++++ .../companyCertificateApiSlice.tsx | 54 ++++++ src/features/store.ts | 8 +- src/types/Config.tsx | 7 + src/types/Constants.ts | 3 + 11 files changed, 550 insertions(+), 4 deletions(-) create mode 100644 src/components/pages/CompanyCertificates/CompanyCertificate.scss create mode 100644 src/components/pages/CompanyCertificates/CompanyCertificateCard.tsx create mode 100644 src/components/pages/CompanyCertificates/CompanyCertificateElements.tsx create mode 100644 src/components/pages/CompanyCertificates/index.tsx create mode 100644 src/features/companyCertification/companyCertificateApiSlice.tsx diff --git a/CHANGELOG.md b/CHANGELOG.md index bb59c7c9f..50f6dc172 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,9 +3,11 @@ ## unreleased 1.8.0-RC3 - Portal login with registration in validation +- Company Certificate + - Provide new link from user menu for the company certificate page + - UI components created to display filter, sort and company certificates - Company Roles - Fetch the standard library data from standards.json and implement Table component to display it in the company roles section. - - ## 1.8.0-RC2 diff --git a/src/assets/locales/de/main.json b/src/assets/locales/de/main.json index c477251e8..d88582d6d 100644 --- a/src/assets/locales/de/main.json +++ b/src/assets/locales/de/main.json @@ -63,6 +63,7 @@ "about": "About", "dataspace": "Data Space", "admin-credential": "Certification Mgmt", + "companyCertificate": "Company Certificates", "companyWallet": "Company Wallet" }, "overlays": { @@ -1701,6 +1702,23 @@ }, "noData": "Derzeit bestehen keine Zertifikate für das Unternehmen. Sie können mit dem Hochladen eines Zertifikats beginnen, indem Sie oben auf die Schaltfläche „Zertifikat hochladen“ klicken." }, + "companyCertificate": { + "heading": "Company Certificates", + "description": "Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard .Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard .", + "tabs": { + "inactive": "Pending", + "active": " Active", + "all": "All" + }, + "sort": { + "name": "Name", + "date": "Date" + }, + "uploadCertificate": "Upload Certificate", + "noData": "Currently there are no certificates for the company. You can start uploading a certificate by clicking the 'Upload Certificate' button above.", + "validtill": "Valid Till", + "morelink": ">> More" + }, "companyWallet": { "heading": "Mein Firmen-Wallet", "description": "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.", diff --git a/src/assets/locales/en/main.json b/src/assets/locales/en/main.json index 8f9be50c4..d0ff2c71d 100644 --- a/src/assets/locales/en/main.json +++ b/src/assets/locales/en/main.json @@ -62,6 +62,7 @@ "about": "About", "dataspace": "Data Space", "admin-credential": "Certification Mgmt", + "companyCertificate": "Company Certificates", "companyWallet": "Company Wallet" }, "overlays": { @@ -1642,6 +1643,23 @@ }, "noData": "Currently there are no certificates for the company. You can start uploading a certificate by clicking the 'Upload Certificate' button above." }, + "companyCertificate": { + "heading": "Company Certificates", + "description": "Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard .Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard .", + "tabs": { + "inactive": "Pending", + "active": " Active", + "all": "All" + }, + "sort": { + "name": "Name", + "date": "Date" + }, + "uploadCertificate": "Upload Certificate", + "noData": "Currently there are no certificates for the company. You can start uploading a certificate by clicking the 'Upload Certificate' button above.", + "validtill": "Valid Till", + "morelink": ">> More" + }, "adminCertificate": { "headline": "Credential Request Overview", "search": "...search for Company Name", diff --git a/src/components/pages/CompanyCertificates/CompanyCertificate.scss b/src/components/pages/CompanyCertificates/CompanyCertificate.scss new file mode 100644 index 000000000..c69619965 --- /dev/null +++ b/src/components/pages/CompanyCertificates/CompanyCertificate.scss @@ -0,0 +1,151 @@ +/******************************************************************************** + * Copyright (c) 2021, 2024 Contributors to the Eclipse Foundation + * + * See the NOTICE file(s) distributed with this work for additional + * information regarding copyright ownership. + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0. + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + * SPDX-License-Identifier: Apache-2.0 + ********************************************************************************/ + +.company-certificate-main { + .company-certificate-section { + margin-top: 72px; + } + + .container { + max-width: 1140px; + margin: 0 auto; + padding: 0 15px; + + .heading { + text-align: center; + } + + .description { + text-align: center; + margin: 34px auto 64px; + width: 70%; + } + + .mainContainer { + width: 100%; + max-width: 1100px; + padding: 0 15px 0 15px !important; + margin-right: auto; + margin-left: auto; + } + + .filterSection { + display: flex; + flex-direction: row; + justify-content: center; + align-items: center; + margin-top: 30px; + margin-bottom: 20px; + } + + .filterSection .chipContainer { + padding-left: 20px; + } + + .sortSection { + position: absolute; + background: #f9f9f9; + box-shadow: 0px 10px 20px rgb(80 80 80 / 30%); + border-radius: 16px; + z-index: 9; + } + + .uploadBtn { + width: 20%; + margin: 0 auto; + margin-bottom: 80px; + } + + .company-certificate-section { + margin: 0 -15px !important; + width: calc(100% + 30px) !important; + + .company-certificate-card { + padding: 0 15px; + margin-bottom: 30px; + } + } + } + + .noData { + text-align: center; + } + + .card-container { + background-color: #fff; + box-shadow: 0px 10px 20px rgb(80 80 80 / 30%); + max-width: 400px; + height: 160px; + display: flex; + flex-direction: row; + justify-content: flex-start; + align-items: flex-start; + padding: 20px 0px; + border-radius: 8px; + + .first-container { + width: 30%; + + img { + width: auto; + height: auto; + } + } + + .second-container { + display: flex; + flex-direction: column; + width: 70%; + justify-content: space-between; + + .top-container { + display: flex; + flex-direction: row; + justify-content: space-between; + padding: 0px 10px; + + .dots { + cursor: pointer; + } + } + + .bottom-container { + padding: 0px 10px; + margin-top: 30px; + display: flex; + flex-direction: column; + + .link { + color: #0f71cb; + cursor: pointer; + } + } + } + } +} + +@media (max-width: 480px) { + .company-certificate-main .container .mainContainer { + padding: 0px !important; + } + + .company-certificate-main .container .uploadBtn { + width: 50%; + } +} diff --git a/src/components/pages/CompanyCertificates/CompanyCertificateCard.tsx b/src/components/pages/CompanyCertificates/CompanyCertificateCard.tsx new file mode 100644 index 000000000..99fcb6db5 --- /dev/null +++ b/src/components/pages/CompanyCertificates/CompanyCertificateCard.tsx @@ -0,0 +1,70 @@ +/******************************************************************************** + * Copyright (c) 2021, 2024 Contributors to the Eclipse Foundation + * + * See the NOTICE file(s) distributed with this work for additional + * information regarding copyright ownership. + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0. + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + * SPDX-License-Identifier: Apache-2.0 + ********************************************************************************/ + +import { useTranslation } from 'react-i18next' +import { Logo, Typography } from '@catena-x/portal-shared-components' +import './CompanyCertificate.scss' +import { type ComapnyCertificateData } from 'features/companyCertification/companyCertificateApiSlice' +import { Box } from '@mui/material' +import { useState } from 'react' +import MoreVertIcon from '@mui/icons-material/MoreVert' + +export default function CompanyCertificateCard({ + item, +}: Readonly<{ + item: ComapnyCertificateData +}>): JSX.Element { + const { t } = useTranslation() + const [dotsMenu, setDotsMenu] = useState(false) + return ( + + + + + + + {item.companyCertificateType} + { + setDotsMenu(!dotsMenu) + }} + > + + + + + + {t('content.companyCertificate.validtill')} : {item.validTill} + + { + // show overlay + }} + > + + {t('content.companyCertificate.morelink')} + + + + + + ) +} diff --git a/src/components/pages/CompanyCertificates/CompanyCertificateElements.tsx b/src/components/pages/CompanyCertificates/CompanyCertificateElements.tsx new file mode 100644 index 000000000..ed250af26 --- /dev/null +++ b/src/components/pages/CompanyCertificates/CompanyCertificateElements.tsx @@ -0,0 +1,58 @@ +/******************************************************************************** + * Copyright (c) 2021, 2024 Contributors to the Eclipse Foundation + * + * See the NOTICE file(s) distributed with this work for additional + * information regarding copyright ownership. + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0. + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + * SPDX-License-Identifier: Apache-2.0 + ********************************************************************************/ + +import { useTranslation } from 'react-i18next' +import { Grid } from '@mui/material' +import { Typography } from '@catena-x/portal-shared-components' +import './CompanyCertificate.scss' +import { type ComapnyCertificateData } from 'features/companyCertification/companyCertificateApiSlice' +import CompanyCertificateCard from './CompanyCertificateCard' + +export default function CompanyCertificateElements({ + data, +}: Readonly<{ + data: ComapnyCertificateData[] +}>): JSX.Element { + const { t } = useTranslation() + + if (data?.length === 0) { + return ( + + {t('content.companyCertificate.noData')} + + ) + } + + return ( + + {data?.map((item: ComapnyCertificateData) => ( + + + + ))} + + ) +} diff --git a/src/components/pages/CompanyCertificates/index.tsx b/src/components/pages/CompanyCertificates/index.tsx new file mode 100644 index 000000000..4cdf43b1f --- /dev/null +++ b/src/components/pages/CompanyCertificates/index.tsx @@ -0,0 +1,163 @@ +/******************************************************************************** + * Copyright (c) 2021, 2024 Contributors to the Eclipse Foundation + * + * See the NOTICE file(s) distributed with this work for additional + * information regarding copyright ownership. + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0. + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + * SPDX-License-Identifier: Apache-2.0 + ********************************************************************************/ + +import { useTranslation, Trans } from 'react-i18next' +import { + Typography, + ViewSelector, + SortOption, + Button, +} from '@catena-x/portal-shared-components' +import SortImage from 'components/shared/frame/SortImage' +import './CompanyCertificate.scss' +import { ROLES } from 'types/Constants' +import CompanyCertificateElements from './CompanyCertificateElements' +import UserService from 'services/UserService' +import { useFetchCertificatesQuery } from 'features/companyCertification/companyCertificateApiSlice' +import { useState } from 'react' +import { Box } from '@mui/material' + +interface TabButtonsType { + buttonText: string + buttonValue: FilterType + onButtonClick: (e: React.MouseEvent) => void +} + +enum FilterType { + ALL = 'All', + INACTIVE = 'Inactive', + ACTIVE = 'Active', +} + +enum SortType { + NEW = 'new', + DATEDESC = 'DateDesc', + TITLE = 'title', + NAMEASC = 'NameAsc', +} + +export default function CompanyCertificates(): JSX.Element { + const { t } = useTranslation() + + const { data } = useFetchCertificatesQuery() + + const [showModal, setShowModal] = useState(false) + const [sortOption, setSortOption] = useState(SortType.NEW) + const [filter, setFilter] = useState(FilterType.ALL) + + const setBtnView = (e: React.MouseEvent): void => { + setFilter(e.currentTarget.value) + } + + const sortOptions = [ + { + label: t('content.companyCertificate.sort.name'), + value: SortType.NEW, + }, + { + label: t('content.companyCertificate.sort.date'), + value: SortType.TITLE, + }, + ] + + const tabButtons: TabButtonsType[] = [ + { + buttonText: t('content.companyCertificate.tabs.all'), + buttonValue: FilterType.ALL, + onButtonClick: setBtnView, + }, + { + buttonText: t('content.companyCertificate.tabs.active'), + buttonValue: FilterType.ACTIVE, + onButtonClick: setBtnView, + }, + { + buttonText: t('content.companyCertificate.tabs.inactive'), + buttonValue: FilterType.INACTIVE, + onButtonClick: setBtnView, + }, + ] + + const handleSortOption = (value: string): void => { + setSortOption(value) + } + + return ( +
+ + + + {t('content.companyCertificate.heading')} + + + + {t('content.companyCertificate.description')} + + + + { + setShowModal(false) + }} + className="filterSection" + > + + + { + setShowModal(true) + }} + selected={showModal} + /> + + + + + + + + + + + + {data != null && } + + +
+ ) +} diff --git a/src/features/companyCertification/companyCertificateApiSlice.tsx b/src/features/companyCertification/companyCertificateApiSlice.tsx new file mode 100644 index 000000000..6c475f72a --- /dev/null +++ b/src/features/companyCertification/companyCertificateApiSlice.tsx @@ -0,0 +1,54 @@ +/******************************************************************************** + * Copyright (c) 2021, 2023 BMW Group AG + * Copyright (c) 2021, 2023 Contributors to the Eclipse Foundation + * + * See the NOTICE file(s) distributed with this work for additional + * information regarding copyright ownership. + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0. + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + * SPDX-License-Identifier: Apache-2.0 + ********************************************************************************/ + +import { createApi, fetchBaseQuery } from '@reduxjs/toolkit/query/react' +import { apiBaseQuery } from 'utils/rtkUtil' + +export type PaginationData = { + totalElements: number + page: number +} + +export type ComapnyCertificateData = { + companyCertificateType: string + companyCertificateStatus: string + documentId: string + validFrom: string + validTill: string +} + +export type CompanyCertificateResponse = { + content: Array + meta: PaginationData +} + +export const apiSlice = createApi({ + reducerPath: 'rtk/admin/companyCertificate', + baseQuery: fetchBaseQuery(apiBaseQuery()), + tagTypes: ['certificate'], + endpoints: (builder) => ({ + fetchCertificates: builder.query({ + query: () => '/api/administration/companydata/companyCertificates ', + providesTags: ['certificate'], + }), + }), +}) + +export const { useFetchCertificatesQuery } = apiSlice diff --git a/src/features/store.ts b/src/features/store.ts index f7c1ad7a0..3cbceea2c 100644 --- a/src/features/store.ts +++ b/src/features/store.ts @@ -67,6 +67,7 @@ import { apiSlice as userManagementApiSlice } from './appManagement/userManageme import { apiSlice as companyWalletApiSlice } from './compayWallet/companyWalletApiSlice' import { apiSlice as deleteCompanyApiSlice } from './deleteCompany/deleteCompanyApiSlice' import { apiSlice as registrationApiSlice } from './registration/registrationApiSlice' +import { apiSlice as companyCertificateApiSlice } from './companyCertification/companyCertificateApiSlice' import { apiSlice as staticContentApiSlice } from './staticContent/staticContentApiSlice' import languageSlice from './language/slice' @@ -124,6 +125,7 @@ export const reducers = { [companyWalletApiSlice.reducerPath]: companyWalletApiSlice.reducer, [deleteCompanyApiSlice.reducerPath]: deleteCompanyApiSlice.reducer, [registrationApiSlice.reducerPath]: registrationApiSlice.reducer, + [companyCertificateApiSlice.reducerPath]: companyCertificateApiSlice.reducer, [staticContentApiSlice.reducerPath]: staticContentApiSlice.reducer, } @@ -156,11 +158,11 @@ export const store = configureStore({ .concat(certificationApiSlice.middleware) .concat(userManagementApiSlice.middleware) .concat(usecaseApiSlice.middleware) - .concat(companyWalletApiSlice.middleware) .concat(registrationApiSlice.middleware) + .concat(companyCertificateApiSlice.middleware) + .concat(companyWalletApiSlice.middleware) .concat(staticContentApiSlice.middleware) - .concat(deleteCompanyApiSlice.middleware) - .concat(registrationApiSlice.middleware), + .concat(deleteCompanyApiSlice.middleware), }) type RootState = ReturnType diff --git a/src/types/Config.tsx b/src/types/Config.tsx index 4d20f9057..7c2db3f9b 100644 --- a/src/types/Config.tsx +++ b/src/types/Config.tsx @@ -82,6 +82,7 @@ import AddRoles from 'components/pages/AppOverview/AddRoles' import ServiceDeactivate from 'components/pages/ServiceReleaseProcess/components/ServiceDeactivate' import ChangeDocuments from 'components/pages/AppOverview/ChangeDocuments' import OSPManagement from 'components/pages/OSPManagement' +import CompanyCertificates from 'components/pages/CompanyCertificates' import CompanyWallet from 'components/pages/CompanyWallet' /** @@ -537,6 +538,11 @@ export const ALL_PAGES: IPage[] = [ role: ROLES.IDP_VIEW, element: , }, + { + name: PAGES.COMPANY_CERTIFICATE, + role: ROLES.COMPANY_CERTIFICATE_VIEW, + element: , + }, { name: PAGES.COMPANY_WALLET, role: ROLES.COMPANY_WALLET, @@ -779,6 +785,7 @@ export const userMenuFull = [ PAGES.USECASE_PARTICIPATION, PAGES.CERTIFICATE_CREDENTIAL, PAGES.ADMIN_CREDENTIAL, + PAGES.COMPANY_CERTIFICATE, PAGES.COMPANY_WALLET, PAGES.LOGOUT, ] diff --git a/src/types/Constants.ts b/src/types/Constants.ts index 34d98461b..077fca7ce 100644 --- a/src/types/Constants.ts +++ b/src/types/Constants.ts @@ -101,6 +101,7 @@ export enum PAGES { DATA_SPACE = 'dataspace', ADMIN_CREDENTIAL = 'admin-credential', ONBOARDING_SERVICEPROVIDER = 'onboarding-serviceprovider', + COMPANY_CERTIFICATE = 'companyCertificate', COMPANY_WALLET = 'companyWallet', DECLINE = 'decline', } @@ -215,6 +216,8 @@ export enum ROLES { SUBMITTED_APPLICATION = 'view_submitted_applications', REQUEST_SSICREDENTIAL = 'request_ssicredential', DECISION_SSICREDENTIAL = 'decision_ssicredential', + COMPANY_CERTIFICATE_VIEW = 'view_certificates', + UPLOAD_COMPANY_CERTIFICATE = 'upload_certificates', COMPANY_WALLET = 'view_wallet', }