Skip to content

Commit 745e33e

Browse files
#179 - Retrieve legacy challenge id for v5 challenge ids
1 parent 8b94415 commit 745e33e

File tree

5 files changed

+103
-12
lines changed

5 files changed

+103
-12
lines changed

config/default.js

+1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ module.exports = {
2222
KAFKA_ERROR_TOPIC: process.env.KAFKA_ERROR_TOPIC || 'error.notification',
2323
KAFKA_AGGREGATE_TOPIC: process.env.KAFKA_AGGREGATE_TOPIC || 'submission.notification.aggregate',
2424
CHALLENGEAPI_URL: process.env.CHALLENGEAPI_URL || 'https://api.topcoder-dev.com/v4/challenges',
25+
CHALLENGEAPI_V5_URL: process.env.CHALLENGEAPI_URL || 'https://api.topcoder-dev.com/v5/challenges',
2526
AUTH0_URL: process.env.AUTH0_URL, // Auth0 credentials for Submission Service
2627
AUTH0_AUDIENCE: process.env.AUTH0_AUDIENCE || 'https://www.topcoder.com',
2728
TOKEN_CACHE_TIME: process.env.TOKEN_CACHE_TIME,

src/common/helper.js

+47-10
Original file line numberDiff line numberDiff line change
@@ -339,6 +339,35 @@ function * getM2Mtoken (parentSpan) {
339339
}
340340
}
341341

342+
/**
343+
* Get legacy challenge id if the challenge id is uuid form
344+
* @param {String} challengeId Challenge ID
345+
* @param {Object} parentSpan the parent Span object
346+
* @returns {String} Legacy Challenge ID of the given challengeId
347+
*/
348+
function * getlegacyChallengeId (challengeId, token, parentSpan) {
349+
if (/^[0-9a-f]{8}-[0-9a-f]{4}-[0-5][0-9a-f]{3}-[089ab][0-9a-f]{3}-[0-9a-f]{12}$/i.test(challengeId)) {
350+
const getlegacyChallengeIdSpan = tracer.startChildSpans('helper.getlegacyChallengeId', parentSpan)
351+
try {
352+
const response = yield request.get(`${config.CHALLENGEAPI_V5_URL}/${challengeId}`)
353+
.set('Authorization', `Bearer ${token}`)
354+
.set('Content-Type', 'application/json')
355+
return response.body.legacyId
356+
} catch (err) {
357+
getlegacyChallengeIdSpan.setTag('error', true)
358+
logger.error(`Error while accessing ${config.CHALLENGEAPI_V5_URL}/${challengeId}`)
359+
getlegacyChallengeIdSpan.log({
360+
event: 'error',
361+
error: err.response.body
362+
})
363+
throw err
364+
} finally {
365+
getlegacyChallengeIdSpan.finish()
366+
}
367+
}
368+
return challengeId
369+
}
370+
342371
/*
343372
* Get submission phase ID of a challenge from Challenge API
344373
* @param challengeId Challenge ID
@@ -352,17 +381,19 @@ function * getSubmissionPhaseId (challengeId, parentSpan) {
352381
try {
353382
let phaseId = null
354383
let response
384+
let legacyChallengeId
355385

356386
const token = yield getM2Mtoken(getSubmissionPhaseIdSpan)
357387

358388
const getChallengePhasesSpan = tracer.startChildSpans('getChallengePhases', getSubmissionPhaseIdSpan)
359389
getChallengePhasesSpan.setTag('challengeId', challengeId)
360390
try {
361-
response = yield request.get(`${config.CHALLENGEAPI_URL}/${challengeId}/phases`)
391+
legacyChallengeId = yield getlegacyChallengeId(challengeId, token, getChallengePhasesSpan)
392+
response = yield request.get(`${config.CHALLENGEAPI_URL}/${legacyChallengeId}/phases`)
362393
.set('Authorization', `Bearer ${token}`)
363394
.set('Content-Type', 'application/json')
364395
} catch (ex) {
365-
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}/${challengeId}/phases`)
396+
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}/${legacyChallengeId}/phases`)
366397
logger.debug('Setting submissionPhaseId to Null')
367398
response = null
368399
// log error
@@ -406,6 +437,7 @@ function * checkCreateAccess (authUser, subEntity, parentSpan) {
406437

407438
try {
408439
let response
440+
let legacyChallengeId
409441

410442
// User can only create submission for themselves
411443
if (authUser.userId !== subEntity.memberId) {
@@ -417,11 +449,12 @@ function * checkCreateAccess (authUser, subEntity, parentSpan) {
417449
const getChallengeDetailSpan = tracer.startChildSpans('getChallengeDetail', checkCreateAccessSpan)
418450
getChallengeDetailSpan.setTag('challengeId', subEntity.challengeId)
419451
try {
420-
response = yield request.get(`${config.CHALLENGEAPI_URL}?filter=id=${subEntity.challengeId}`)
452+
legacyChallengeId = yield getlegacyChallengeId(subEntity.challengeId, token, getChallengeDetailSpan)
453+
response = yield request.get(`${config.CHALLENGEAPI_URL}?filter=id=${legacyChallengeId}`)
421454
.set('Authorization', `Bearer ${token}`)
422455
.set('Content-Type', 'application/json')
423456
} catch (ex) {
424-
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}?filter=id=${subEntity.challengeId}`)
457+
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}?filter=id=${legacyChallengeId}`)
425458
logger.error(ex)
426459
// log error
427460
getChallengeDetailSpan.log({
@@ -473,6 +506,7 @@ function * checkGetAccess (authUser, submission, parentSpan) {
473506
try {
474507
let resources
475508
let challengeDetails
509+
let legacyChallengeId
476510
// Allow downloading Own submission
477511
if (submission.memberId === authUser.userId) {
478512
return true
@@ -483,11 +517,12 @@ function * checkGetAccess (authUser, submission, parentSpan) {
483517
const getChallengeResourcesSpan = tracer.startChildSpans('getChallengeResources', checkGetAccessSpan)
484518
getChallengeResourcesSpan.setTag('challengeId', submission.challengeId)
485519
try {
486-
resources = yield request.get(`${config.CHALLENGEAPI_URL}/${submission.challengeId}/resources`)
520+
legacyChallengeId = yield getlegacyChallengeId(submission.challengeId, token, getChallengeResourcesSpan)
521+
resources = yield request.get(`${config.CHALLENGEAPI_URL}/${legacyChallengeId}/resources`)
487522
.set('Authorization', `Bearer ${token}`)
488523
.set('Content-Type', 'application/json')
489524
} catch (ex) {
490-
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}/${submission.challengeId}/resources`)
525+
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}/${legacyChallengeId}/resources`)
491526
logger.error(ex)
492527
// log error
493528
getChallengeResourcesSpan.log({
@@ -503,11 +538,11 @@ function * checkGetAccess (authUser, submission, parentSpan) {
503538
const getChallengeDetailSpan = tracer.startChildSpans('getChallengeDetail', checkGetAccessSpan)
504539
getChallengeDetailSpan.setTag('challengeId', submission.challengeId)
505540
try {
506-
challengeDetails = yield request.get(`${config.CHALLENGEAPI_URL}?filter=id=${submission.challengeId}`)
541+
challengeDetails = yield request.get(`${config.CHALLENGEAPI_URL}?filter=id=${legacyChallengeId}`)
507542
.set('Authorization', `Bearer ${token}`)
508543
.set('Content-Type', 'application/json')
509544
} catch (ex) {
510-
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}?filter=id=${submission.challengeId}`)
545+
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}?filter=id=${legacyChallengeId}`)
511546
logger.error(ex)
512547
// log error
513548
getChallengeDetailSpan.log({
@@ -601,16 +636,18 @@ function * checkReviewGetAccess (authUser, submission, parentSpan) {
601636

602637
try {
603638
let challengeDetails
639+
let legacyChallengeId
604640
const token = yield getM2Mtoken(checkReviewGetAccessSpan)
605641

606642
const getChallengeDetailSpan = tracer.startChildSpans('getChallengeDetail', checkReviewGetAccessSpan)
607643
getChallengeDetailSpan.setTag('challengeId', submission.challengeId)
608644
try {
609-
challengeDetails = yield request.get(`${config.CHALLENGEAPI_URL}?filter=id=${submission.challengeId}`)
645+
legacyChallengeId = yield getlegacyChallengeId(submission.challengeId, token, getChallengeDetailSpan)
646+
challengeDetails = yield request.get(`${config.CHALLENGEAPI_URL}?filter=id=${legacyChallengeId}`)
610647
.set('Authorization', `Bearer ${token}`)
611648
.set('Content-Type', 'application/json')
612649
} catch (ex) {
613-
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}?filter=id=${submission.challengeId}`)
650+
logger.error(`Error while accessing ${config.CHALLENGEAPI_URL}?filter=id=${legacyChallengeId}`)
614651

615652
// log error
616653
getChallengeDetailSpan.log({

test/common/testData.js

+33
Original file line numberDiff line numberDiff line change
@@ -766,6 +766,38 @@ const testReviewSummationsES = {
766766
}
767767
}
768768

769+
const testChallengeV5APIResponse = {
770+
id: '60bde5f2-aadc-4c64-aa74-523081a1e394',
771+
typeId: '',
772+
track: 'track',
773+
name: `a B c challenge`,
774+
description: 'desc',
775+
challengeSettings: [{ type: '', value: 'value' }],
776+
timelineTemplateId: '',
777+
phases: [],
778+
prizeSets: [{
779+
type: 'ChallengePrizes',
780+
description: 'ddd',
781+
prizes: [{
782+
description: 'some prize',
783+
type: 'type',
784+
value: 800
785+
}]
786+
}],
787+
reviewType: 'review type',
788+
tags: ['tag1'],
789+
projectId: 111,
790+
legacyId: '30054692',
791+
forumId: 333,
792+
termsIds: [21343, 20723],
793+
startDate: '2015-07-27T09:19Z',
794+
status: 'active',
795+
groups: ['group1'],
796+
gitRepoURLs: ['https://mozilla.org/?x=%D1%88%D0%B5%D0%BB%D0%BB%D1%8B'],
797+
created: '2015-07-27T09:19Z',
798+
createdBy: 'admin'
799+
}
800+
769801
const testChallengeAPIResponse = {
770802
id: '24a97f2f:1655fef5034:-7568',
771803
result: {
@@ -953,6 +985,7 @@ module.exports = {
953985
testReviewSummationES,
954986
testReviewSummationsES,
955987
testChallengeAPIResponse,
988+
testChallengeV5APIResponse,
956989
testChallengeDetailResponse,
957990
testSubmissionWoLegacyES,
958991
testSubmissionWReview

test/unit/SubmissionService.test.js

+19-2
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ const should = chai.should() // eslint-disable-line
1515
const app = require('../../app')
1616
const {
1717
nonExSubmissionId, testSubmission, testSubmissionWoLegacy,
18-
testSubmissionPatch, testSubmissionWReview
18+
testSubmissionPatch, testSubmissionWReview, testChallengeV5APIResponse
1919
} = require('../common/testData')
2020

2121
chai.use(chaiHttp)
@@ -187,7 +187,7 @@ describe('Submission Service tests', () => {
187187
.attach('submission', './test/common/fileToUpload.zip', 'fileToUpload.zip')
188188
.end((err, res) => {
189189
res.should.have.status(400)
190-
res.body.message.should.be.eql('Either file to be uploaded or URL should be present')
190+
res.body.message.should.be.eql('Either file to be uploaded or URL should be present. Not both.')
191191
done()
192192
})
193193
})
@@ -294,6 +294,23 @@ describe('Submission Service tests', () => {
294294
done()
295295
})
296296
}).timeout(10000)
297+
298+
it('Creating a submission using v5 challenge id should succeed', (done) => {
299+
chai.request(app)
300+
.post(`${config.API_VERSION}/submissions`)
301+
.set('Authorization', `Bearer ${config.ADMIN_TOKEN}`)
302+
.send(_.extend(_.omit(testSubmission.Item, ['id', 'created', 'updated', 'createdBy', 'updatedBy', 'submissionPhaseId', 'challengeId']), {challengeId: testChallengeV5APIResponse.id}))
303+
.end((err, res) => {
304+
res.should.have.status(200)
305+
res.body.should.have.keys(Object.keys(_.extend({ fileType: 'zip' }, testSubmission.Item)))
306+
res.body.id.should.not.be.eql(null)
307+
res.body.challengeId.should.be.eql(testChallengeV5APIResponse.id)
308+
res.body.type.should.be.eql(testSubmission.Item.type)
309+
res.body.url.should.be.eql(testSubmission.Item.url)
310+
res.body.fileType.should.be.eql('zip')
311+
done()
312+
})
313+
}).timeout(10000)
297314
})
298315

299316
/*

test/unit/prepare.js

+3
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,7 @@ prepare(function (done) {
102102
const busUrl = URL.parse(config.BUSAPI_EVENTS_URL)
103103
const challengeApiUrl = URL.parse(`${config.CHALLENGEAPI_URL}/${testData.testSubmissionWoLegacy.Item.challengeId}/phases`)
104104
const challengeApiUrl2 = URL.parse(`${config.CHALLENGEAPI_URL}/${testData.testSubmission.Item.challengeId}/phases`)
105+
const challengeV5ApiUrl = URL.parse(`${config.CHALLENGEAPI_V5_URL}/${testData.testChallengeV5APIResponse.id}`)
105106
const challengeDetailUrl = URL.parse(`${config.CHALLENGEAPI_URL}?filter=id=${testData.testSubmission.Item.challengeId}`)
106107
const challengeWoLegacyUrl = URL.parse(`${config.CHALLENGEAPI_URL}?filter=id=${testData.testSubmissionWoLegacy.Item.challengeId}`)
107108

@@ -129,6 +130,8 @@ prepare(function (done) {
129130
.reply(200, { access_token: jwt.sign({user: 'test', exp: 9999999999999999}, config.AUTH_SECRET) })
130131
.post(busUrl.path)
131132
.reply(204)
133+
.get(challengeV5ApiUrl.path)
134+
.reply(200, testData.testChallengeV5APIResponse)
132135
.get(challengeApiUrl.path)
133136
.reply(200, testData.testChallengeAPIResponse)
134137
.get(challengeApiUrl2.path)

0 commit comments

Comments
 (0)