From b2c2c3c5bc58395dab020a436af6f694f32b8f93 Mon Sep 17 00:00:00 2001 From: Pratiyush Kumar <82165483+Pratiyushkumar@users.noreply.github.com> Date: Sat, 5 Aug 2023 22:55:39 +0530 Subject: [PATCH] Provide super user option on member detail page (#536) * Provide super user option on member detail page * able to render isMember and isArchived value * addressed the changes suggested by vinayak * adding api integration in the feature * removed comments * added condition for default behaviour control * made a generalized functions and added conditon to variable and use it * updated the member promotion and archive member functions --- src/components/keyboard-handler/index.js | 7 +- src/components/member-profile/index.js | 34 +++++-- .../member-profile/member-profile.module.scss | 4 + src/components/member-role-update/index.js | 89 +++++++++++++------ src/helper-functions/action-handlers.js | 14 +-- src/helper-functions/urls.js | 8 +- 6 files changed, 104 insertions(+), 52 deletions(-) diff --git a/src/components/keyboard-handler/index.js b/src/components/keyboard-handler/index.js index 4a395217..e2e60fee 100644 --- a/src/components/keyboard-handler/index.js +++ b/src/components/keyboard-handler/index.js @@ -3,8 +3,11 @@ import { useKeyboardContext } from '@store/keyboard/context'; import { ALT_KEY } from '@constants/AppConstants'; function isOptionKey(e) { - e.preventDefault(); - return e.key === ALT_KEY; + if (e.key === ALT_KEY) { + e.preventDefault(); + return true; + } + return false; } function KeyboardHandler({ children }) { diff --git a/src/components/member-profile/index.js b/src/components/member-profile/index.js index 9cd3c9b0..6048d9ce 100644 --- a/src/components/member-profile/index.js +++ b/src/components/member-profile/index.js @@ -1,5 +1,6 @@ /* eslint-disable react/no-array-index-key */ import React, { useRef, useState } from 'react'; +import { useRouter } from 'next/router'; import PropTypes from 'prop-types'; import SocialMediaIcon from '@components/social-media-icon'; import getBadges from '@components/member-profile/mock/get-badges'; @@ -14,6 +15,9 @@ import { KEY_ESC, KEY_TAB } from '@constants/AppConstants'; import MemberTaskUpdate from '@components/member-task-update'; import { useTaskContext } from '@store/tasks/tasks-context'; import { userContext } from '@store/user/user-context'; +import { useKeyboardContext } from '@store/keyboard/context'; +import SuperUserOptions from '@components/member-card/super-user-options'; +import MemberRoleUpdate from '@components/member-role-update'; const renderBadgeImages = (badges) => badges.map((badge) => ( @@ -66,25 +70,28 @@ const Profile = (props) => { } = props; const { membersData } = props; const isMember = Boolean(membersData?.roles?.member); + const memberStatusMessage = isMember ? 'User is a Member' : 'User is not a Member'; - + const { showMemberRoleUpdateModal, isSuperUser } = userContext(); const socialMedia = [ 'twitter_id', 'github_id', 'linkedin_id', 'instagram_id', ]; + const { query } = useRouter() || { query: { dev: false } }; + const { dev } = query; const { showMemberTaskUpdateModal } = useTaskContext(); - const { isSuperUser } = userContext(); const fullName = `${first_name} ${last_name}`; const memberName = fullName.trim() || '--'; const rdsUserName = `@${username}`; const badges = getBadges(username); - + const { isOptionKeyPressed } = useKeyboardContext(); + const [showSettings, setShowSettings] = useState(false); const [showModal, setShowModal] = useState(false); const { register, handleSubmit, errors } = useForm(); const submitBtnRef = useRef(null); @@ -360,6 +367,8 @@ const Profile = (props) => { e.target.src = '/images/Avatar.png'; }; + const superUserOptionKeyPress = dev && isSuperUser && isOptionKeyPressed; + return ( <> {showModal && ( @@ -367,6 +376,11 @@ const Profile = (props) => { {children} )} + {isSuperUser && ( +
+ {showMemberRoleUpdateModal && } +
+ )} {showMemberTaskUpdateModal && }
@@ -378,8 +392,12 @@ const Profile = (props) => { className={classNames.profilePic} alt={fullName} /> - {isSuperUser && ( -
+ {superUserOptionKeyPress && ( +
setShowSettings(true)} + onMouseLeave={() => setShowSettings(false)} + > info icon { height={20} /> {memberStatusMessage} + + +
)} diff --git a/src/components/member-profile/member-profile.module.scss b/src/components/member-profile/member-profile.module.scss index e6b2fd6f..ffa9e5e0 100644 --- a/src/components/member-profile/member-profile.module.scss +++ b/src/components/member-profile/member-profile.module.scss @@ -216,6 +216,10 @@ width: 1rem; } +.showSettingsButton { + margin-left: 0.8rem; +} + .hidden { display: none; } diff --git a/src/components/member-role-update/index.js b/src/components/member-role-update/index.js index c8e9c423..1b9ae427 100644 --- a/src/components/member-role-update/index.js +++ b/src/components/member-role-update/index.js @@ -7,10 +7,7 @@ import MemberTagAssign from '@components/member-tag-assign'; import { BASE_API_URL } from '@constants/AppConstants'; import useFetch from '@custom-hooks/useFetch'; import classNames from './member-role-update.module.scss'; -import { - archiveMember, - moveToMember, -} from '../../helper-functions/action-handlers'; +import { memberRoleUpdate } from '../../helper-functions/action-handlers'; const MemberRoleUpdate = () => { const { @@ -26,48 +23,82 @@ const MemberRoleUpdate = () => { `${BASE_API_URL}/users/${selectedMember}` ); + const member = userData?.user?.roles.member; + const archived = userData?.user?.roles.archived; + const userId = userData?.user.id; const { data: tagData } = useFetch(`${BASE_API_URL}/tags`); const { data: levelData } = useFetch(`${BASE_API_URL}/levels`); - const promoteToMember = async (user) => { + const promoteDemoteAMember = async (id) => { + let memberRole = null; setIsUpdating(true); - const { status } = await moveToMember(user); - setIsUpdating(false); - if (status === 204) { - setUpdateStatus('User moved to member'); + if (member) { + memberRole = false; } else { - setUpdateStatus('Some error occured, please contact admin'); + memberRole = true; + } + const role = { + member: memberRole, + }; + try { + const { status } = await memberRoleUpdate(id, role); + setIsUpdating(false); + if (status === 200) { + setUpdateStatus('user promoted to a member'); + } + } catch (error) { + setUpdateStatus('some error occured, please contact admin'); } }; - const archiveTheMember = async (user) => { + + const archiveUnArchiveTheMember = async (id) => { + let archiveRole = null; setIsUpdating(true); - const { status } = await archiveMember(user); - setIsUpdating(false); - if (status === 204) { - setUpdateStatus('User archived!'); + if (archived) { + archiveRole = false; } else { + archiveRole = true; + } + const role = { + archived: archiveRole, + }; + try { + const { status } = await memberRoleUpdate(id, role); + setIsUpdating(false); + if (status === 200) { + setUpdateStatus('user archived!'); + } + } catch (error) { setUpdateStatus('Some error occured, please contact admin'); } }; + const memberRoleUpdateButton = ( + + ); + + const memeberArchiveUnArchiveButton = ( + + ); + const renderPromoteButton = () => { return ( <> - + {memberRoleUpdateButton} + {memeberArchiveUnArchiveButton} -
{userData && tagData && levelData && ( diff --git a/src/helper-functions/action-handlers.js b/src/helper-functions/action-handlers.js index 99b389b6..a8363afc 100644 --- a/src/helper-functions/action-handlers.js +++ b/src/helper-functions/action-handlers.js @@ -1,14 +1,13 @@ import { fetch } from './fetch'; import { - getAddMemberRoleURL, getUserProfileSelf, - getArchiveMemberURL, getTaskUpdateURL, getTagAssignURL, + updateMemberRole, } from './urls'; -const moveToMember = (user) => - fetch(getAddMemberRoleURL(user), 'patch', null, null, null, { +const memberRoleUpdate = (user, role) => + fetch(updateMemberRole(user), 'patch', null, role, null, { withCredentials: true, }); @@ -17,11 +16,6 @@ const getUserSelf = () => withCredentials: true, }); -const archiveMember = (user) => - fetch(getArchiveMemberURL(user), 'patch', null, null, null, { - withCredentials: true, - }); - const moveTask = (taskId, data) => fetch( getTaskUpdateURL(taskId), @@ -46,4 +40,4 @@ const assignTags = (data) => } ); -export { archiveMember, moveToMember, getUserSelf, moveTask, assignTags }; +export { getUserSelf, moveTask, assignTags, memberRoleUpdate }; diff --git a/src/helper-functions/urls.js b/src/helper-functions/urls.js index f938985b..03e9e408 100644 --- a/src/helper-functions/urls.js +++ b/src/helper-functions/urls.js @@ -40,11 +40,8 @@ const getActiveTasksURL = (rdsId) => `${baseURL}/tasks/${rdsId}?status=active`; * * @param {string} rdsId */ -const getAddMemberRoleURL = (rdsId) => - `${baseURL}/members/moveToMembers/${rdsId}`; -const getArchiveMemberURL = (rdsId) => - `${baseURL}/members/archiveMembers/${rdsId}`; +const updateMemberRole = (rdsId) => `${baseURL}/users/${rdsId}/temporary/data`; /** * @@ -62,8 +59,7 @@ export { getCloudinaryImgURL, getActiveTasksURL, getUserProfileSelf, - getAddMemberRoleURL, - getArchiveMemberURL, getTaskUpdateURL, getTagAssignURL, + updateMemberRole, };