Skip to content

Commit ba34ea0

Browse files
committed
1 parent 6a1758e commit ba34ea0

File tree

12 files changed

+212
-21
lines changed

12 files changed

+212
-21
lines changed

src/actions/challenges.js

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import {
1515
fetchChallengeTracks,
1616
updateChallenge,
1717
patchChallenge,
18+
deleteChallenge as deleteChallengeAPI,
1819
createChallenge as createChallengeAPI,
1920
createResource as createResourceAPI,
2021
deleteResource as deleteResourceAPI
@@ -38,6 +39,9 @@ import {
3839
CREATE_CHALLENGE_PENDING,
3940
CREATE_CHALLENGE_SUCCESS,
4041
CREATE_CHALLENGE_FAILURE,
42+
DELETE_CHALLENGE_PENDING,
43+
DELETE_CHALLENGE_SUCCESS,
44+
DELETE_CHALLENGE_FAILURE,
4145
LOAD_CHALLENGE_RESOURCES
4246
} from '../config/constants'
4347
import { loadProject } from './projects'
@@ -267,6 +271,26 @@ export function partiallyUpdateChallengeDetails (challengeId, partialChallengeDe
267271
}
268272
}
269273

274+
export function deleteChallenge (challengeId) {
275+
return async (dispatch) => {
276+
dispatch({
277+
type: DELETE_CHALLENGE_PENDING
278+
})
279+
280+
return deleteChallengeAPI(challengeId).then((challenge) => {
281+
return dispatch({
282+
type: DELETE_CHALLENGE_SUCCESS,
283+
challengeDetails: challenge
284+
})
285+
}).catch((error) => {
286+
dispatch({
287+
type: DELETE_CHALLENGE_FAILURE
288+
})
289+
throw error
290+
})
291+
}
292+
}
293+
270294
export function loadTimelineTemplates () {
271295
return async (dispatch) => {
272296
const timelineTemplates = await fetchTimelineTemplates()

src/components/ChallengeEditor/ChallengeEditor.module.scss

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -241,7 +241,7 @@
241241
.actionButtons {
242242
position: absolute;
243243
top: 30px;
244-
a {
244+
a,button {
245245
height: 40px;
246246
}
247247
}
@@ -251,7 +251,13 @@
251251
}
252252

253253
.actionButtonsRight {
254+
display: flex;
255+
align-items: center;
254256
right: 20px;
257+
258+
button {
259+
margin-right: 20px;
260+
}
255261
}
256262

257263
.buttonContainer {

src/components/ChallengeEditor/index.js

Lines changed: 43 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ class ChallengeEditor extends Component {
6868
super(props)
6969
this.state = {
7070
isLaunch: false,
71+
isDeleteLaunch: false,
7172
isConfirm: false,
7273
isClose: false,
7374
isOpenAdvanceSettings: false,
@@ -121,6 +122,8 @@ class ChallengeEditor extends Component {
121122
this.getAvailableTimelineTemplates = this.getAvailableTimelineTemplates.bind(this)
122123
this.autoUpdateChallengeThrottled = _.throttle(this.validateAndAutoUpdateChallenge.bind(this), 3000) // 3s
123124
this.updateResource = this.updateResource.bind(this)
125+
this.onDeleteChallenge = this.onDeleteChallenge.bind(this)
126+
this.deleteModalLaunch = this.deleteModalLaunch.bind(this)
124127
}
125128

126129
componentDidMount () {
@@ -131,6 +134,29 @@ class ChallengeEditor extends Component {
131134
this.resetChallengeData(this.setState.bind(this))
132135
}
133136

137+
deleteModalLaunch () {
138+
if (!this.state.isDeleteLaunch) {
139+
this.setState({ isDeleteLaunch: true })
140+
}
141+
}
142+
143+
async onDeleteChallenge () {
144+
const { deleteChallenge, challengeDetails, history } = this.props
145+
console.log(challengeDetails, deleteChallenge)
146+
try {
147+
this.setState({ isSaving: true })
148+
// Call action to delete the challenge
149+
await deleteChallenge(challengeDetails.id)
150+
this.setState({ isSaving: false })
151+
this.resetModal()
152+
history.push(`/projects/${challengeDetails.projectId}/challenges`)
153+
} catch (e) {
154+
const error = _.get(e, 'response.data.message', 'Unable to Delete the challenge')
155+
console.log(error)
156+
this.setState({ isSaving: false, error })
157+
}
158+
}
159+
134160
/**
135161
* Validates challenge and if its valid calling an autosave method
136162
*
@@ -206,7 +232,7 @@ class ChallengeEditor extends Component {
206232
}
207233

208234
resetModal () {
209-
this.setState({ isLoading: false, isConfirm: false, isLaunch: false, error: null, isCloseTask: false })
235+
this.setState({ isLoading: false, isConfirm: false, isLaunch: false, error: null, isCloseTask: false, isDeleteLaunch: false })
210236
}
211237

212238
/**
@@ -1373,6 +1399,19 @@ class ChallengeEditor extends Component {
13731399
/>
13741400
</div>
13751401
}
1402+
{
1403+
this.state.isDeleteLaunch && !this.state.isConfirm && (
1404+
<ConfirmationModal
1405+
title='Confirm Delete'
1406+
message={`Do you want to delete "${challenge.name}"?`}
1407+
theme={theme}
1408+
isProcessing={isSaving}
1409+
errorMessage={this.state.error}
1410+
onCancel={this.resetModal}
1411+
onConfirm={this.onDeleteChallenge}
1412+
/>
1413+
)
1414+
}
13761415
{ showTimeline && (
13771416
<ChallengeScheduleField
13781417
templates={this.getAvailableTimelineTemplates()}
@@ -1426,6 +1465,7 @@ class ChallengeEditor extends Component {
14261465
</div>
14271466
<div className={styles.title}>{getTitle(isNew)}</div>
14281467
<div className={cn(styles.actionButtons, styles.actionButtonsRight)}>
1468+
{this.props.challengeDetails.status === 'New' && <PrimaryButton text={'Delete'} type={'danger'} onClick={this.deleteModalLaunch} />}
14291469
<PrimaryButton text={'Back'} type={'info'} submit link={`/projects/${projectDetail.id}/challenges`} />
14301470
</div>
14311471
<div className={styles.textRequired}>* Required</div>
@@ -1469,7 +1509,8 @@ ChallengeEditor.propTypes = {
14691509
updateChallengeDetails: PropTypes.func.isRequired,
14701510
createChallenge: PropTypes.func,
14711511
replaceResourceInRole: PropTypes.func,
1472-
partiallyUpdateChallengeDetails: PropTypes.func.isRequired
1512+
partiallyUpdateChallengeDetails: PropTypes.func.isRequired,
1513+
deleteChallenge: PropTypes.func.isRequired
14731514
}
14741515

14751516
export default withRouter(ChallengeEditor)

src/components/ChallengesComponent/ChallengeCard/ChallengeCard.module.scss

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -257,6 +257,31 @@
257257
}
258258
}
259259

260+
.deleteButton {
261+
height: 22px;
262+
width: 86px;
263+
border-radius: 11.5px;
264+
display: flex;
265+
justify-content: center;
266+
align-items: center;
267+
background-color: $tc-red;
268+
border-color: $tc-red;
269+
cursor: pointer;
270+
271+
span {
272+
@include roboto;
273+
274+
font-size: 14px;
275+
font-weight: 400;
276+
line-height: 17px;
277+
color: $white;
278+
text-transform: capitalize;
279+
display: flex;
280+
justify-content: center;
281+
align-items: center;
282+
}
283+
}
284+
260285
.icon {
261286
vertical-align: bottom;
262287
}

src/components/ChallengesComponent/ChallengeCard/index.js

Lines changed: 51 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -96,14 +96,20 @@ const getPhaseInfo = (c) => {
9696
* @param onUpdateLaunch
9797
* @returns {*}
9898
*/
99-
const hoverComponents = (challenge, onUpdateLaunch) => {
99+
const hoverComponents = (challenge, onUpdateLaunch, deleteModalLaunch) => {
100100
const communityAppUrl = `${COMMUNITY_APP_URL}/challenges/${challenge.id}`
101101
const directUrl = `${DIRECT_PROJECT_URL}/contest/detail?projectId=${challenge.legacyId}`
102102
const orUrl = `${ONLINE_REVIEW_URL}/review/actions/ViewProjectDetails?pid=${challenge.legacyId}`
103103

104104
// NEW projects never have Legacy challenge created, so don't show links and "Activate" button for them at all
105105
if (challenge.status.toUpperCase() === CHALLENGE_STATUS.NEW) {
106-
return null
106+
if (challenge.status.toUpperCase() === CHALLENGE_STATUS.NEW) {
107+
return (
108+
<button className={styles.deleteButton} onClick={() => deleteModalLaunch()}>
109+
<span>Delete</span>
110+
</button>
111+
)
112+
}
107113
}
108114

109115
return challenge.legacyId ? (
@@ -177,10 +183,13 @@ class ChallengeCard extends React.Component {
177183
this.state = {
178184
isConfirm: false,
179185
isLaunch: false,
186+
isDeleteLaunch: false,
180187
isSaving: false
181188
}
182189
this.onUpdateConfirm = this.onUpdateConfirm.bind(this)
183190
this.onUpdateLaunch = this.onUpdateLaunch.bind(this)
191+
this.onDeleteChallenge = this.onDeleteChallenge.bind(this)
192+
this.deleteModalLaunch = this.deleteModalLaunch.bind(this)
184193
this.resetModal = this.resetModal.bind(this)
185194
this.onLaunchChallenge = this.onLaunchChallenge.bind(this)
186195
}
@@ -195,8 +204,14 @@ class ChallengeCard extends React.Component {
195204
}
196205
}
197206

207+
deleteModalLaunch () {
208+
if (!this.state.isDeleteLaunch) {
209+
this.setState({ isDeleteLaunch: true })
210+
}
211+
}
212+
198213
resetModal () {
199-
this.setState({ isConfirm: false, isLaunch: false })
214+
this.setState({ isConfirm: false, isLaunch: false, isDeleteLaunch: false })
200215
}
201216

202217
async onLaunchChallenge () {
@@ -216,12 +231,39 @@ class ChallengeCard extends React.Component {
216231
}
217232
}
218233

234+
async onDeleteChallenge () {
235+
const { deleteChallenge, challenge } = this.props
236+
try {
237+
this.setState({ isSaving: true })
238+
// Call action to delete the challenge
239+
await deleteChallenge(challenge.id)
240+
this.setState({ isSaving: false })
241+
this.resetModal()
242+
} catch (e) {
243+
const error = _.get(e, 'response.data.message', 'Unable to Delete the challenge')
244+
this.setState({ isSaving: false, error })
245+
}
246+
}
247+
219248
render () {
220-
const { isLaunch, isConfirm, isSaving } = this.state
249+
const { isLaunch, isConfirm, isSaving, isDeleteLaunch } = this.state
221250
const { challenge, shouldShowCurrentPhase, reloadChallengeList } = this.props
222251
const { phaseMessage, endTime } = getPhaseInfo(challenge)
223252
return (
224253
<div className={styles.item}>
254+
{
255+
isDeleteLaunch && !isConfirm && (
256+
<ConfirmationModal
257+
title='Confirm Delete'
258+
message={`Do you want to delete "${challenge.name}"?`}
259+
theme={theme}
260+
isProcessing={isSaving}
261+
errorMessage={this.state.error}
262+
onCancel={this.resetModal}
263+
onConfirm={this.onDeleteChallenge}
264+
/>
265+
)
266+
}
225267
{ isLaunch && !isConfirm && (
226268
<ConfirmationModal
227269
title='Confirm Launch'
@@ -263,7 +305,7 @@ class ChallengeCard extends React.Component {
263305
<span className='block light-text'>{endTime}</span>
264306
</Link>)}
265307
<div className={cn(styles.col4, styles.editingContainer)}>
266-
{hoverComponents(challenge, this.onUpdateLaunch, this.props.showError)}
308+
{hoverComponents(challenge, this.onUpdateLaunch, this.deleteModalLaunch)}
267309
</div>
268310
<div className={cn(styles.col4, styles.iconsContainer)}>
269311
<div className={styles.faIconContainer}>
@@ -282,16 +324,17 @@ class ChallengeCard extends React.Component {
282324

283325
ChallengeCard.defaultPrps = {
284326
shouldShowCurrentPhase: true,
285-
showError: () => {},
327+
// showError: () => {},
286328
reloadChallengeList: () => {}
287329
}
288330

289331
ChallengeCard.propTypes = {
290332
challenge: PropTypes.object,
291333
shouldShowCurrentPhase: PropTypes.bool,
292-
showError: PropTypes.func,
334+
// showError: PropTypes.func,
293335
reloadChallengeList: PropTypes.func,
294-
partiallyUpdateChallengeDetails: PropTypes.func.isRequired
336+
partiallyUpdateChallengeDetails: PropTypes.func.isRequired,
337+
deleteChallenge: PropTypes.func.isRequired
295338
}
296339

297340
export default withRouter(ChallengeCard)

src/components/ChallengesComponent/ChallengeList/index.js

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,8 @@ class ChallengeList extends Component {
102102
page,
103103
perPage,
104104
totalChallenges,
105-
partiallyUpdateChallengeDetails
105+
partiallyUpdateChallengeDetails,
106+
deleteChallenge
106107
} = this.props
107108
if (warnMessage) {
108109
return <Message warnMessage={warnMessage} />
@@ -214,6 +215,7 @@ class ChallengeList extends Component {
214215
showError={this.showError}
215216
reloadChallengeList={this.reloadChallengeList}
216217
partiallyUpdateChallengeDetails={partiallyUpdateChallengeDetails}
218+
deleteChallenge={deleteChallenge}
217219
/>
218220
</li>
219221
)
@@ -256,7 +258,8 @@ ChallengeList.propTypes = {
256258
page: PropTypes.number.isRequired,
257259
perPage: PropTypes.number.isRequired,
258260
totalChallenges: PropTypes.number.isRequired,
259-
partiallyUpdateChallengeDetails: PropTypes.func.isRequired
261+
partiallyUpdateChallengeDetails: PropTypes.func.isRequired,
262+
deleteChallenge: PropTypes.func.isRequired
260263
}
261264

262265
export default ChallengeList

src/components/ChallengesComponent/index.js

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,8 @@ const ChallengesComponent = ({
2626
page,
2727
perPage,
2828
totalChallenges,
29-
partiallyUpdateChallengeDetails
29+
partiallyUpdateChallengeDetails,
30+
deleteChallenge
3031
}) => {
3132
return (
3233
<Sticky top={10}>
@@ -86,6 +87,7 @@ const ChallengesComponent = ({
8687
perPage={perPage}
8788
totalChallenges={totalChallenges}
8889
partiallyUpdateChallengeDetails={partiallyUpdateChallengeDetails}
90+
deleteChallenge={deleteChallenge}
8991
/>
9092
)}
9193
</div>
@@ -109,7 +111,8 @@ ChallengesComponent.propTypes = {
109111
page: PropTypes.number.isRequired,
110112
perPage: PropTypes.number.isRequired,
111113
totalChallenges: PropTypes.number.isRequired,
112-
partiallyUpdateChallengeDetails: PropTypes.func.isRequired
114+
partiallyUpdateChallengeDetails: PropTypes.func.isRequired,
115+
deleteChallenge: PropTypes.func.isRequired
113116
}
114117

115118
ChallengesComponent.defaultProps = {

src/config/constants.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,10 @@ export const CREATE_CHALLENGE_SUCCESS = 'CREATE_CHALLENGE_SUCCESS'
4848
export const CREATE_CHALLENGE_PENDING = 'CREATE_CHALLENGE_PENDING'
4949
export const CREATE_CHALLENGE_FAILURE = 'CREATE_CHALLENGE_FAILURE'
5050

51+
export const DELETE_CHALLENGE_SUCCESS = 'DELETE_CHALLENGE_SUCCESS'
52+
export const DELETE_CHALLENGE_PENDING = 'DELETE_CHALLENGE_PENDING'
53+
export const DELETE_CHALLENGE_FAILURE = 'DELETE_CHALLENGE_FAILURE'
54+
5155
export const LOAD_PROJECT_DETAILS = 'LOAD_PROJECT_DETAILS'
5256
export const LOAD_PROJECT_DETAILS_SUCCESS = 'LOAD_PROJECT_DETAILS_SUCCESS'
5357
export const LOAD_PROJECT_DETAILS_PENDING = 'LOAD_PROJECT_DETAILS_PENDING'

0 commit comments

Comments
 (0)