Skip to content
This repository was archived by the owner on Mar 13, 2025. It is now read-only.

Permissions part 2 - permission based on Project Roles (members) #110

Merged
merged 2 commits into from
Feb 23, 2021
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
feat: candidate accept/reject permissions
ref issue #100
  • Loading branch information
maxceem committed Feb 23, 2021
commit f18605eca3791868bebd50aba8436c2022de789d
36 changes: 24 additions & 12 deletions src/constants/permissions.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
*
* Examples of CORRECT permission naming and meaning:
* - `VIEW_PROJECT`
* - `EDIT_MILESTONE`
* - `UPDATE_MILESTONE`
* - `DELETE_WORK`
*
* Examples of INCORRECT permissions naming and meaning:
Expand Down Expand Up @@ -78,31 +78,43 @@ export const PROJECT_ROLE = {

export const PERMISSIONS = {
/**
* Resource Booking
* Job
*/
EDIT_RESOURCE_BOOKING: {
UPDATE_JOB_STATUS: {
meta: {
group: "Resource Booking",
title: "Edit Resource Booking",
group: "Job",
title: 'Edit Job "status"',
},
topcoderRoles: [TOPCODER_ROLE.BOOKING_MANAGER, TOPCODER_ROLE.ADMINISTRATOR],
},

ACCESS_RESOURCE_BOOKING_MEMBER_RATE: {
/**
* Job Candidate
*/
UPDATE_JOB_CANDIDATE: {
meta: {
group: "Resource Booking",
title: "Access Member Rate (view and edit)",
group: "Job Candidate",
title: 'Update Job Candidate',
},
projectRoles: true,
topcoderRoles: [TOPCODER_ROLE.BOOKING_MANAGER, TOPCODER_ROLE.ADMINISTRATOR],
},

/**
* Job
* Resource Booking
*/
EDIT_JOB_STATUS: {
UPDATE_RESOURCE_BOOKING: {
meta: {
group: "Job",
title: 'Edit Job "status"',
group: "Resource Booking",
title: "Edit Resource Booking",
},
topcoderRoles: [TOPCODER_ROLE.BOOKING_MANAGER, TOPCODER_ROLE.ADMINISTRATOR],
},

ACCESS_RESOURCE_BOOKING_MEMBER_RATE: {
meta: {
group: "Resource Booking",
title: "Access Member Rate (view and edit)",
},
topcoderRoles: [TOPCODER_ROLE.BOOKING_MANAGER, TOPCODER_ROLE.ADMINISTRATOR],
},
Expand Down
9 changes: 5 additions & 4 deletions src/hoc/withAuthentication/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ import { useParams } from "@reach/router";
export default function withAuthentication(Component) {
const AuthenticatedComponent = (props) => {
const dispatch = useDispatch();
const { isLoggedIn, authError, teamId } = useSelector(
const { isLoggedIn, authError, teamId, teamMembersLoaded, teamMembersLoadingError } = useSelector(
(state) => state.authUser
);
const params = useParams();
Expand Down Expand Up @@ -85,11 +85,12 @@ export default function withAuthentication(Component) {
return (
<>
{/* Show loading indicator until we know if user is logged-in or no.
Also, show loading indicator if we need to know team members but haven't loaded them yet.
In we got error during this process, show error */}
{isLoggedIn === null && <LoadingIndicator error={authError} />}
{isLoggedIn === null || (params.teamId && !teamMembersLoaded) && <LoadingIndicator error={authError || teamMembersLoadingError} />}

{/* Show component only if user is logged-in */}
{isLoggedIn === true ? <Component {...props} /> : null}
{/* Show component only if user is logged-in and if we don't need team members or we already loaded them */}
{isLoggedIn === true && (!params.teamId || teamMembersLoaded) ? <Component {...props} /> : null}
</>
);
};
Expand Down
4 changes: 4 additions & 0 deletions src/hoc/withAuthentication/reducers/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ const initialState = {
teamMembers: undefined,
teamMembersLoading: undefined,
teamMembersLoadingError: undefined,
teamMembersLoaded: false,
};

const authInitialState = _.pick(initialState, [
Expand Down Expand Up @@ -56,6 +57,7 @@ const reducer = (state = initialState, action) => {
teamMembers: initialState.teamMembersLoadingError,
teamMembersLoading: true,
teamMembersLoadingError: initialState.teamMembersLoadingError,
teamMembersLoaded: false,
};

case ACTION_TYPE.AUTH_LOAD_TEAM_MEMBERS_SUCCESS: {
Expand All @@ -65,6 +67,7 @@ const reducer = (state = initialState, action) => {
...state,
teamMembersLoading: false,
teamMembers: action.payload,
teamMembersLoaded: true,
};
}

Expand All @@ -78,6 +81,7 @@ const reducer = (state = initialState, action) => {
...state,
teamMembersLoading: false,
teamMembersLoadingError: action.payload,
teamMembersLoaded: false,
};
}

Expand Down
2 changes: 1 addition & 1 deletion src/routes/JobForm/utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ export const getEditJobConfig = (skillOptions, onSubmit) => {
validationMessage: "Please, select Status",
name: "status",
selectOptions: STATUS_OPTIONS,
disabled: !hasPermission(PERMISSIONS.EDIT_JOB_STATUS),
disabled: !hasPermission(PERMISSIONS.UPDATE_JOB_STATUS),
},
],
onSubmit: onSubmit,
Expand Down
4 changes: 2 additions & 2 deletions src/routes/MyTeamsDetails/components/TeamMembers/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -158,11 +158,11 @@ const TeamMembers = ({ team }) => {
`/taas/myteams/${team.id}/rb/${member.id}/edit`
);
},
hidden: !hasPermission(PERMISSIONS.EDIT_RESOURCE_BOOKING),
hidden: !hasPermission(PERMISSIONS.UPDATE_RESOURCE_BOOKING),
},
{
separator: true,
hidden: !hasPermission(PERMISSIONS.EDIT_RESOURCE_BOOKING),
hidden: !hasPermission(PERMISSIONS.UPDATE_RESOURCE_BOOKING),
},
{
label: "Report an Issue",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ import Pagination from "components/Pagination";
import IconResume from "../../../../assets/images/icon-resume.svg";
import { toastr } from "react-redux-toastr";
import { getJobById } from "services/jobs";
import { PERMISSIONS } from "constants/permissions";
import { hasPermission } from "utils/permissions";

/**
* Generates a function to sort candidates
Expand Down Expand Up @@ -192,7 +194,7 @@ const PositionCandidates = ({ position, candidateStatus, updateCandidate }) => {
)}
</div>
<div styleName="table-cell cell-action">
{candidateStatus === CANDIDATE_STATUS.OPEN && (
{candidateStatus === CANDIDATE_STATUS.OPEN && hasPermission(PERMISSIONS.UPDATE_JOB_CANDIDATE) && (
<>
Interested in this candidate?
<div styleName="actions">
Expand Down
2 changes: 1 addition & 1 deletion src/routes/ResourceBookingDetails/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ const ResourceBookingDetails = ({ teamId, resourceBookingId }) => {
<div styleName="content-wrapper">
<ResourceSummary member={member} />
<ResourceDetails resource={resource} jobTitle={jobTitle} />
{hasPermission(PERMISSIONS.EDIT_RESOURCE_BOOKING) && (
{hasPermission(PERMISSIONS.UPDATE_RESOURCE_BOOKING) && (
<div styleName="actions">
<Button
size="medium"
Expand Down
4 changes: 2 additions & 2 deletions src/routes/ResourceBookingForm/utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import {
import { hasPermission } from "utils/permissions";
import { PERMISSIONS } from "constants/permissions";

const EDIT_RESOURCE_BOOKING_ROWS = [
const UPDATE_RESOURCE_BOOKING_ROWS = [
{ type: FORM_ROW_TYPE.SINGLE, fields: ["handle"] },
{ type: FORM_ROW_TYPE.SINGLE, fields: ["jobTitle"] },
{ type: FORM_ROW_TYPE.GROUP, fields: ["startDate", "endDate"] },
Expand Down Expand Up @@ -99,6 +99,6 @@ export const getEditResourceBookingConfig = (onSubmit) => {
},
],
onSubmit: onSubmit,
rows: EDIT_RESOURCE_BOOKING_ROWS,
rows: UPDATE_RESOURCE_BOOKING_ROWS,
};
};