diff --git a/src/cml.js b/src/cml.js index 10576bef0..e25def7a6 100755 --- a/src/cml.js +++ b/src/cml.js @@ -82,9 +82,19 @@ class CML { this.driver = driver || inferDriver({ repo: this.repo }); } + async revParse({ ref = 'HEAD' } = {}) { + try { + return await exec(`git rev-parse ${ref}`); + } catch (err) { + winston.warn( + 'Failed to obtain SHA. Perhaps not in the correct git folder' + ); + } + } + async triggerSha() { const { sha } = getDriver(this); - return sha || (await exec(`git rev-parse HEAD`)); + return sha || (await this.revParse()); } async branch() { @@ -93,14 +103,18 @@ class CML { } async commentCreate(opts = {}) { + const triggerSha = await this.triggerSha(); const { report: userReport, - commitSha = await this.triggerSha(), + commitSha: inCommitSha = triggerSha, rmWatermark, update, pr } = opts; + const commitSha = + (await this.revParse({ ref: inCommitSha })) || inCommitSha; + if (rmWatermark && update) throw new Error('watermarks are mandatory for updateable comments'); @@ -118,40 +132,42 @@ class CML { }); }; - if (pr || this.driver === 'bitbucket') { + const isBB = this.driver === BB; + if (pr || isBB) { let commentUrl; - if ( - (await exec(`git rev-parse ${commitSha}`)) !== - (await exec('git rev-parse HEAD')) - ) + if (commitSha !== triggerSha) winston.info( - `Looking for PR associated with --commit-sha="${commitSha}".\nSee https://cml.dev/doc/ref/send-comment.` + `Looking for PR associated with --commit-sha="${inCommitSha}".\nSee https://cml.dev/doc/ref/send-comment.` ); + const longReport = `${commitSha.substr(0, 7)}\n\n${report}`; const [commitPr = {}] = await drv.commitPrs({ commitSha }); const { url } = commitPr; - if (!url) throw new Error(`PR for commit sha "${commitSha}" not found`); + if (!url && !isBB) + throw new Error(`PR for commit sha "${inCommitSha}" not found`); - const [prNumber] = url.split('/').slice(-1); + if (url) { + const [prNumber] = url.split('/').slice(-1); - if (update) - comment = updatableComment(await drv.prComments({ prNumber })); + if (update) + comment = updatableComment(await drv.prComments({ prNumber })); - if (update && comment) { - commentUrl = await drv.prCommentUpdate({ - report: longReport, - id: comment.id, - prNumber - }); - } else - commentUrl = await drv.prCommentCreate({ - report: longReport, - prNumber - }); + if (update && comment) { + commentUrl = await drv.prCommentUpdate({ + report: longReport, + id: comment.id, + prNumber + }); + } else + commentUrl = await drv.prCommentCreate({ + report: longReport, + prNumber + }); - if (this.driver !== 'bitbucket') return commentUrl; + if (this.driver !== 'bitbucket') return commentUrl; + } } if (update) diff --git a/src/drivers/bitbucket_cloud.js b/src/drivers/bitbucket_cloud.js index c89998f55..a057f1957 100644 --- a/src/drivers/bitbucket_cloud.js +++ b/src/drivers/bitbucket_cloud.js @@ -66,26 +66,18 @@ class BitbucketCloud { const { projectPath } = this; const { commitSha, state = 'OPEN' } = opts; - try { - const endpoint = `/repositories/${projectPath}/commit/${commitSha}/pullrequests?state=${state}`; - const prs = await this.paginatedRequest({ endpoint }); - - return prs.map((pr) => { - const { - links: { - html: { href: url } - } - } = pr; - return { - url - }; - }); - } catch (err) { - if (err.message === 'Not Found Resource not found') - err.message = - "Click 'Go to pull request' on any commit details page to enable this API"; - throw err; - } + const endpoint = `/repositories/${projectPath}/commit/${commitSha}/pullrequests?state=${state}`; + const prs = await this.paginatedRequest({ endpoint }); + return prs.map((pr) => { + const { + links: { + html: { href: url } + } + } = pr; + return { + url + }; + }); } async checkCreate() { @@ -222,9 +214,30 @@ class BitbucketCloud { throw new Error('BitBucket Cloud does not support workflowRestart!'); } + async pipelineJobs(opts = {}) { + throw new Error('Not implemented'); + } + + async paginatedRequest(opts = {}) { + const { method = 'GET', body } = opts; + const { next, values } = await this.request(opts); + + if (next) { + const nextValues = await this.paginatedRequest({ + url: next, + method, + body + }); + values.push(...nextValues); + } + + return values; + } + async request(opts = {}) { const { token, api } = this; const { url, endpoint, method = 'GET', body } = opts; + if (!(url || endpoint)) throw new Error('Bitbucket Cloud API endpoint not found'); const headers = { @@ -249,26 +262,6 @@ class BitbucketCloud { return await response.json(); } - async pipelineJobs(opts = {}) { - throw new Error('Not implemented'); - } - - async paginatedRequest(opts = {}) { - const { method = 'GET', body } = opts; - const { next, values } = await this.request(opts); - - if (next) { - const nextValues = await this.paginatedRequest({ - url: next, - method, - body - }); - values.push(...nextValues); - } - - return values; - } - get sha() { return BITBUCKET_COMMIT; }