diff --git a/src/App.tsx b/src/App.tsx index f78778bb1a..fbb394bc9d 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -30,7 +30,7 @@ import CommunityProfile from 'screens/CommunityProfile/CommunityProfile'; import OrganizationVenues from 'screens/OrganizationVenues/OrganizationVenues'; import Leaderboard from 'screens/Leaderboard/Leaderboard'; -import React from 'react'; +import React, { useEffect } from 'react'; // User Portal Components import Donate from 'screens/UserPortal/Donate/Donate'; import Events from 'screens/UserPortal/Events/Events'; @@ -38,16 +38,21 @@ import Posts from 'screens/UserPortal/Posts/Posts'; import Organizations from 'screens/UserPortal/Organizations/Organizations'; import People from 'screens/UserPortal/People/People'; import Settings from 'screens/UserPortal/Settings/Settings'; -import Chat from 'screens/UserPortal/Chat/Chat'; +// import Chat from 'screens/UserPortal/Chat/Chat'; +import { useQuery } from '@apollo/client'; +import { CHECK_AUTH } from 'GraphQl/Queries/Queries'; import Advertisements from 'components/Advertisements/Advertisements'; import SecuredRouteForUser from 'components/UserPortal/SecuredRouteForUser/SecuredRouteForUser'; + +import useLocalStorage from 'utils/useLocalstorage'; import UserScreen from 'screens/UserPortal/UserScreen/UserScreen'; import EventDashboardScreen from 'components/EventDashboardScreen/EventDashboardScreen'; import Campaigns from 'screens/UserPortal/Campaigns/Campaigns'; import Pledges from 'screens/UserPortal/Pledges/Pledges'; import VolunteerManagement from 'screens/UserPortal/Volunteer/VolunteerManagement'; +import LeaveOrganization from 'screens/UserPortal/LeaveOrganization/LeaveOrganization'; -// const { setItem } = useLocalStorage(); +const { setItem } = useLocalStorage(); /** * This is the main function for our application. It sets up all the routes and components, @@ -92,20 +97,21 @@ function app(): JSX.Element { // TODO: Fetch Installed plugin extras and store for use within MainContent and Side Panel Components. - // const { data, loading } = useQuery(CHECK_AUTH); + const { data, loading } = useQuery(CHECK_AUTH); - // useEffect(() => { - // if (data) { - // setItem('name', `${data.checkAuth.firstName} ${data.checkAuth.lastName}`); - // setItem('id', data.checkAuth._id); - // setItem('email', data.checkAuth.email); - // setItem('IsLoggedIn', 'TRUE'); - // setItem('FirstName', data.checkAuth.firstName); - // setItem('LastName', data.checkAuth.lastName); - // setItem('UserImage', data.checkAuth.image); - // setItem('Email', data.checkAuth.email); - // } - // }, [data, loading]); + useEffect(() => { + if (!loading && data?.checkAuth) { + const auth = data.checkAuth; + setItem('IsLoggedIn', 'TRUE'); + setItem('id', auth._id); + setItem('name', `${auth.firstName} ${auth.lastName}`); + setItem('FirstName', auth.firstName); + setItem('LastName', auth.lastName); + setItem('email', auth.email); + setItem('Email', auth.email); + setItem('UserImage', auth.image); + } + }, [data, loading, setItem]); const extraRoutes = Object.entries(installedPlugins).map( ( @@ -192,9 +198,12 @@ function app(): JSX.Element { } /> } /> } /> - } /> } /> } /> + } + /> } @@ -207,6 +216,7 @@ function app(): JSX.Element { + {/* */} } /> diff --git a/src/screens/UserPortal/People/People.spec.tsx b/src/screens/UserPortal/People/People.spec.tsx index 51fb5d2767..8837bee265 100644 --- a/src/screens/UserPortal/People/People.spec.tsx +++ b/src/screens/UserPortal/People/People.spec.tsx @@ -11,7 +11,7 @@ import { Provider } from 'react-redux'; import { store } from 'state/store'; import i18nForTest from 'utils/i18nForTest'; import { StaticMockLink } from 'utils/StaticMockLink'; -import type { InterfaceMember } from './People'; +// import type { InterfaceMember } from './People'; import People from './People'; import userEvent from '@testing-library/user-event'; import { vi } from 'vitest'; @@ -168,62 +168,6 @@ describe('Testing People Screen [User Portal]', () => { expect(screen.queryAllByText('Noble Mittal')).not.toBe([]); }); - function compareProperties( - expectedProps: string[], - actualObject: object, - ): boolean { - const actualProps = Object.keys(actualObject); - return expectedProps.every((prop) => actualProps.includes(prop)); - } - - describe('InterfaceMember properties comparison', () => { - it('should have all required properties', () => { - const expectedProperties = [ - 'firstName', - 'lastName', - 'image', - '_id', - 'email', - '__typename', - ]; - - const mockValidData: InterfaceMember = { - firstName: 'John', - lastName: 'Doe', - image: 'https://example.com/john.jpg', - _id: '1', - email: 'john.doe@example.com', - __typename: 'User', - }; - - const result = compareProperties(expectedProperties, mockValidData); - expect(result).toBe(true); - }); - - it('should fail if __typename is replaced with username', () => { - const expectedProperties = [ - 'firstName', - 'lastName', - 'image', - '_id', - 'email', - '__typename', // Expect this property - ]; - - const mockInvalidData = { - firstName: 'John', - lastName: 'Doe', - image: 'https://example.com/john.jpg', - _id: '1', - email: 'john.doe@example.com', - username: 'Member', // Incorrect property - }; - - const result = compareProperties(expectedProperties, mockInvalidData); - expect(result).toBe(false); - }); - }); - it('Search works properly by pressing enter', async () => { render( diff --git a/src/screens/UserPortal/People/People.tsx b/src/screens/UserPortal/People/People.tsx index 6dfac868da..827a5b49c6 100644 --- a/src/screens/UserPortal/People/People.tsx +++ b/src/screens/UserPortal/People/People.tsx @@ -22,13 +22,13 @@ interface InterfaceOrganizationCardProps { sno: string; } -export interface InterfaceMember { +interface InterfaceMember { firstName: string; lastName: string; image: string; _id: string; email: string; - __typename: string; + userType: string; } /** @@ -37,20 +37,19 @@ export interface InterfaceMember { * and paginate through the list. */ export default function people(): JSX.Element { - // i18n translation hook for user organization related translations const { t } = useTranslation('translation', { keyPrefix: 'people', }); - // i18n translation hook for common translations const { t: tCommon } = useTranslation('common'); - // State for managing current page in pagination const [page, setPage] = useState(0); // State for managing the number of rows per page in pagination const [rowsPerPage, setRowsPerPage] = useState(5); - const [members, setMembers] = useState([]); + const [members, setMembers] = useState([]); + const [allMembers, setAllMembers] = useState([]); + const [admins, setAdmins] = useState([]); const [mode, setMode] = useState(0); // Extracting organization ID from URL parameters @@ -69,17 +68,11 @@ export default function people(): JSX.Element { }, }, ); - // Query to fetch list of admins of the organization const { data: data2 } = useQuery(ORGANIZATION_ADMINS_LIST, { variables: { id: organizationId }, }); - /** - * Handles page change in pagination. - * - */ - /* istanbul ignore next */ const handleChangePage = ( _event: React.MouseEvent | null, newPage: number, @@ -87,11 +80,6 @@ export default function people(): JSX.Element { setPage(newPage); }; - /** - * Handles change in the number of rows per page. - * - */ - /* istanbul ignore next */ const handleChangeRowsPerPage = ( event: React.ChangeEvent, ): void => { @@ -101,20 +89,12 @@ export default function people(): JSX.Element { setPage(0); }; - /** - * Searches for members based on the filter value. - * - */ const handleSearch = (newFilter: string): void => { refetch({ firstName_contains: newFilter, }); }; - /** - * Handles search operation triggered by pressing the Enter key. - * - */ const handleSearchByEnter = ( e: React.KeyboardEvent, ): void => { @@ -124,9 +104,6 @@ export default function people(): JSX.Element { } }; - /** - * Handles search operation triggered by clicking the search button. - */ const handleSearchByBtnClick = (): void => { const inputValue = (document.getElementById('searchPeople') as HTMLInputElement)?.value || @@ -134,24 +111,51 @@ export default function people(): JSX.Element { handleSearch(inputValue); }; + useEffect(() => { + if (data2) { + const admin = data2.organizations[0].admins[0]; + const updatedAdmin: InterfaceMember = { + ...admin, + userType: 'Admin', + }; + setAdmins([updatedAdmin]); + } + }, [data2]); + useEffect(() => { if (data) { - setMembers(data.organizationsMemberConnection.edges); + const updatedAdmins = data.organizationsMemberConnection.edges.map( + (memberData: InterfaceMember) => ({ + ...memberData, // Spread the existing properties + userType: admins?.some((admin) => admin._id === memberData._id) + ? 'Admin' + : 'Member', + }), + ); + + setAllMembers(updatedAdmins); + setMembers(updatedAdmins); } - }, [data]); + }, [data, admins]); - /** - * Updates the list of members based on the selected filter mode. - */ - /* istanbul ignore next */ + if (admins && admins.length > 0) { + const adminIds = admins.map((adm) => adm._id); + for (let i = 0; i < allMembers.length; i++) { + if (adminIds.includes(allMembers[i]._id)) { + allMembers[i].userType = 'Admin'; + } else { + allMembers[i].userType = 'Member'; + } + } + } useEffect(() => { if (mode == 0) { if (data) { - setMembers(data.organizationsMemberConnection.edges); + setMembers(allMembers); } } else if (mode == 1) { if (data2) { - setMembers(data2.organizations[0].admins); + setMembers(admins); } } }, [mode]); @@ -243,7 +247,7 @@ export default function people(): JSX.Element { image: member.image, id: member._id, email: member.email, - role: member.__typename, + role: member.userType, sno: (index + 1).toString(), }; return ;