Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
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
2 changes: 1 addition & 1 deletion .circleci/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -297,7 +297,7 @@ workflows:
filters:
branches:
only:
- free
- gig-apply-restrict
# This is stage env for production QA releases
- "build-prod-staging":
context : org-global
Expand Down
28 changes: 21 additions & 7 deletions src/server/services/recruitCRM.js
Original file line number Diff line number Diff line change
Expand Up @@ -308,15 +308,29 @@ export default class RecruitCRMService {
error: true,
status: candidateResponse.status,
url: `${this.private.baseUrl}/v1/candidates/search?email=${form.email}`,
errObj: await candidateResponse.json(),
errorObj: await candidateResponse.json(),
};
notifyKirilAndNick(error);
return res.send(error);
}
let candidateData = await candidateResponse.json();
if (candidateData.data) {
// Candidate exists we will update profile fields
// otherwise we create it
// Candidate exists in recruitCRM
// We will update profile fields, otherwise we create new candidate below
// Check if candidate is placed in gig currently
const candStatusIndex = _.findIndex(
candidateData.data[0].custom_fields, { field_id: 12 },
);
if (candStatusIndex !== -1 && candidateData.data[0].custom_fields[candStatusIndex].value === 'Placed') {
// reject application
return res.send({
error: true,
errorObj: {
notAllowed: true,
message: 'Apologies, you are not allowed to apply to gigs if you are already placed on a gig.',
},
});
}
candidateSlug = candidateData.data[0].slug;
const fieldIndexProfile = _.findIndex(
candidateData.data[0].custom_fields, { field_id: 14 },
Expand Down Expand Up @@ -345,7 +359,7 @@ export default class RecruitCRMService {
status: workCandidateResponse.status,
url: `${this.private.baseUrl}/v1/candidates${candidateSlug ? `/${candidateSlug}` : ''}`,
form,
errObj: await workCandidateResponse.json(),
errorObj: await workCandidateResponse.json(),
};
notifyKirilAndNick(error);
return res.send(error);
Expand All @@ -371,7 +385,7 @@ export default class RecruitCRMService {
fileData,
file,
formHeaders,
errObj: await fileCandidateResponse.json(),
errorObj: await fileCandidateResponse.json(),
};
notifyKirilAndNick(error);
return res.send(error);
Expand Down Expand Up @@ -399,7 +413,7 @@ export default class RecruitCRMService {
url: `${this.private.baseUrl}/v1/candidates/${candidateData.slug}/assign?job_slug=${id}`,
form,
candidateData,
errObj,
errorObj: errObj,
};
notifyKirilAndNick(error);
return res.send(error);
Expand All @@ -423,7 +437,7 @@ export default class RecruitCRMService {
status: hireStageResponse.status,
url: `$${this.private.baseUrl}/v1/candidates/${candidateData.slug}/hiring-stages/${id}`,
form,
errObj: await hireStageResponse.json(),
errorObj: await hireStageResponse.json(),
};
notifyKirilAndNick(error);
return res.send(error);
Expand Down
123 changes: 75 additions & 48 deletions src/shared/components/Gigs/GigApply/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ export default function GigApply(props) {
} = props;
const retUrl = window.location.href;
const duration = getCustomField(job.custom_fields, 'Duration');
const isPlaced = _.find(_.isEmpty(recruitProfile) ? [] : recruitProfile.custom_fields, { field_id: 12 });

return user ? (
<div styleName="container">
Expand All @@ -45,10 +46,24 @@ export default function GigApply(props) {
<h2>{job.name}</h2>
<Link to={`${config.GIGS_PAGES_PATH}/${job.slug}`} styleName="back-link"><BackArrowGig /> GIG DETAILS</Link>
<div styleName="separator" />
{
isPlaced && isPlaced.value === 'Placed' ? (
<div styleName="apply-state">
<SadFace />
<h2>One Gig Limit!</h2>
<React.Fragment>
<p>Apologies, you are not allowed to apply to gigs if you are already placed on a gig.<br /><br />You can however refer a friend to this gig and receive $500 if they get placed in that gig. To do that, you can enter their email on the right side of the Gigs Description page.<br /><br />If you have any questions or feel this is an error, please email <a href="mailto:gigwork@topcoder.com">gigwork@topcoder.com</a>.</p>
</React.Fragment>
<div styleName="cta-buttons">
<Link to={`${config.GIGS_PAGES_PATH}/${job.slug}`} styleName="primaryBtn">Back To Gig</Link>
</div>
</div>
) : null
}
{
application ? (
<div styleName="apply-state">
{ application.error ? <SadFace /> : <img src={bigCheckmark} alt="bigCheckmark OK" /> }
{ application.error ? <SadFace /> : <img src={bigCheckmark} alt="bigCheckmark OK" />}
<h2>{application.error ? 'OOPS!' : 'APPLICATION SUBMITTED'}</h2>
{
application.error ? (
Expand All @@ -58,8 +73,16 @@ export default function GigApply(props) {
<p styleName="error-text">{application.errorObj.message || JSON.stringify(application.errorObj)}</p>
) : null
}
<p>Looks like there is a problem on our end. Please try again.<br />If this persists please contact <a href="mailto:support@topcoder.com">support@topcoder.com</a>.</p>
<p>Please send us an email at <a href="mailto:gigwork@topcoder.com">gigwork@topcoder.com</a> with the subject ‘Gig Error’<br />and paste the URL for the gig you are attempting to apply for so that we know of your interest.</p>
{
application.errorObj && application.errorObj.notAllowed ? (
<p>If you have any questions or feel this is an error, please email <a href="mailto:gigwork@topcoder.com">gigwork@topcoder.com</a>.</p>
) : (
<React.Fragment>
<p>Looks like there is a problem on our end. Please try again.<br />If this persists please contact <a href="mailto:support@topcoder.com">support@topcoder.com</a>.</p>
<p>Please send us an email at <a href="mailto:gigwork@topcoder.com">gigwork@topcoder.com</a> with the subject ‘Gig Error’<br />and paste the URL for the gig you are attempting to apply for so that we know of your interest.</p>
</React.Fragment>
)
}
</React.Fragment>
) : (
<p>We will contact you via email if it seems like a fit!</p>
Expand All @@ -69,15 +92,19 @@ export default function GigApply(props) {
{
application.error ? (
<React.Fragment>
<a
href="#"
styleName="primaryBtn"
onClick={(e) => {
e.preventDefault();
window.location.reload();
}}
>APPLY AGAIN
</a>
{
!application.errorObj.notAllowed ? (
<a
href="#"
styleName="primaryBtn"
onClick={(e) => {
e.preventDefault();
window.location.reload();
}}
>APPLY AGAIN
</a>
) : null
}
<Link to={`${config.GIGS_PAGES_PATH}`}>VIEW OTHER GIGS</Link>
</React.Fragment>
) : (
Expand All @@ -97,18 +124,18 @@ export default function GigApply(props) {
) : null
}
{
!application && !applying ? (
!application && !applying && (!isPlaced || isPlaced.value !== 'Placed') ? (
<div styleName="form-wrap">
{!_.isEmpty(recruitProfile)
&& (
<div styleName="info-text">
<h6>It looks like you have applied to a gig previously. Perfect!<CheckmarkGreen /></h6>
<p>We have most of your information. Is there anything you would like to update to your Gig Work Profile?</p>
</div>
)}
&& (
<div styleName="info-text">
<h6>It looks like you have applied to a gig previously. Perfect!<CheckmarkGreen /></h6>
<p>We have most of your information. Is there anything you would like to update to your Gig Work Profile?</p>
</div>
)}
<h4>PERSONAL INFORMATION</h4>
{_.isEmpty(recruitProfile)
&& <p>Welcome to Topcoder Gigs! We’d like to get to know you.</p>}
&& <p>Welcome to Topcoder Gigs! We’d like to get to know you.</p>}
<div styleName="form-section">
<div styleName="form-row">
<TextInput
Expand Down Expand Up @@ -170,26 +197,26 @@ export default function GigApply(props) {
</div>
{_.isEmpty(recruitProfile) && <h4>TOPCODER INFORMATION</h4>}
{_.isEmpty(recruitProfile) && (
<div styleName="form-section">
<div styleName="form-row">
<TextInput
placeholder="Topcoder Username"
label="Topcoder Username"
onChange={val => onFormInputChange('handle', val)}
errorMsg={formErrors.handle}
value={formData.handle}
readonly
/>
<TextInput
placeholder="Topcoder Profile (topcoder.com/members/[username])"
label="Topcoder Profile"
onChange={val => onFormInputChange('tcProfileLink', val)}
errorMsg={formErrors.tcProfileLink}
value={formData.handle ? `https://topcoder.com/members/${formData.handle}` : null}
readonly
/>
<div styleName="form-section">
<div styleName="form-row">
<TextInput
placeholder="Topcoder Username"
label="Topcoder Username"
onChange={val => onFormInputChange('handle', val)}
errorMsg={formErrors.handle}
value={formData.handle}
readonly
/>
<TextInput
placeholder="Topcoder Profile (topcoder.com/members/[username])"
label="Topcoder Profile"
onChange={val => onFormInputChange('tcProfileLink', val)}
errorMsg={formErrors.tcProfileLink}
value={formData.handle ? `https://topcoder.com/members/${formData.handle}` : null}
readonly
/>
</div>
</div>
</div>
)}
<h4>SHARE YOUR WEEKLY PAY EXPECTATIONS</h4>
<div styleName="form-section">
Expand Down Expand Up @@ -236,14 +263,14 @@ export default function GigApply(props) {
<h4>FINAL QUESTIONS</h4>
<div styleName="form-section">
{_.isEmpty(recruitProfile) && (
<Dropdown
placeholder="How did you find out about Topcoder Gig Work?"
label="How did you find out about Topcoder Gig Work?"
onChange={val => onFormInputChange('reffereal', val)}
errorMsg={formErrors.reffereal}
options={formData.reffereal}
required
/>
<Dropdown
placeholder="How did you find out about Topcoder Gig Work?"
label="How did you find out about Topcoder Gig Work?"
onChange={val => onFormInputChange('reffereal', val)}
errorMsg={formErrors.reffereal}
options={formData.reffereal}
required
/>
)}
<div styleName="input-bot-margin" />
<p>Are you able to work during the specified timezone? (<strong>{`${getCustomField(job.custom_fields, 'Timezone')}`}</strong>) *</p>
Expand Down Expand Up @@ -283,7 +310,7 @@ export default function GigApply(props) {
</button>
</div>
) : null
}
}
</div>
)
}
Expand Down