From 90066427ecfa2abf2ee83f499ecea2fe989ce18c Mon Sep 17 00:00:00 2001 From: therussiankid92 <38100922+therussiankid92@users.noreply.github.com> Date: Wed, 3 Jun 2020 17:35:53 +0200 Subject: [PATCH] feature: seti-587 prevent labeler fail (#9) * feature: [SETI-587] - added hard-failure input --- .env.dist | 2 +- .github/workflows/check-no-deploy-window.yml | 4 +- .github/workflows/test.yml | 3 +- README.MD | 3 +- action.yml | 4 ++ dist/index.js | 55 +++++++++++++++++-- src/application/index.js | 9 ++- src/infrastructure/constants.js | 2 + src/infrastructure/github-actions.js | 40 +++++++++++++- .../tests/github-actions.test.js | 52 ++++++++++++++++++ 10 files changed, 160 insertions(+), 14 deletions(-) diff --git a/.env.dist b/.env.dist index 1ee5ed2..a995688 100644 --- a/.env.dist +++ b/.env.dist @@ -3,4 +3,4 @@ REPOSITORY_NAME= LABEL_ACTION= LABEL= BASE_BRANCH= - +HARD_FAILURE= diff --git a/.github/workflows/check-no-deploy-window.yml b/.github/workflows/check-no-deploy-window.yml index c6f05f2..13dfa47 100644 --- a/.github/workflows/check-no-deploy-window.yml +++ b/.github/workflows/check-no-deploy-window.yml @@ -10,7 +10,7 @@ jobs: name: check no deploy window steps: - name: is deploy calendar busy? - uses: Typeform/siesta@v1 + uses: Typeform/siesta@v1.1 id: siesta with: google-credentials: ${{ secrets.siesta_google_credentials }} @@ -19,6 +19,7 @@ jobs: custom-calendar-busy-message: 'There is an event in the Calendar. Deploying not recommended.' custom-calendar-not-busy-message: 'No event in the Calendar. Feel free to deploy.' fail-if-busy: false + hard-failure: true - name: set label action based on result uses: haya14busa/action-cond@v1.0.0 id: condval @@ -35,3 +36,4 @@ jobs: label: no-deploy-window label-action: ${{steps.condval.outputs.value}} base-branch: master + hard-failure: true diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index cc4aa3f..a4b8098 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -14,8 +14,9 @@ jobs: uses: ./ id: labeler with: - github-token: ${{ secrets.labeler_github_token }} + github-token: ${{ secrets.GITHUB_TOKEN }} repository-name: ${{ github.repository }} label-action: add label: LABELER_TEST base-branch: master + hard-failure: true diff --git a/README.MD b/README.MD index 0a7d23c..b7c3579 100644 --- a/README.MD +++ b/README.MD @@ -8,7 +8,8 @@ A Github Action that helps you to add and remove labels of all PRs in a given re ```label_action```: Mandatory, option between add or remove ```label```: Mandatory, how you want to name your label ```base-branch```: Optional, filter pulls by base branch name. Default: all base branches - +```hard-failure```: Optional, boolean, if true, fails the build on any error. If false, throws an warning instead. Default is false. + ## Contributing All code should pass tests, as well as be well documented. [Please also see the Commit Message Guidelines](CONTRIBUTING.MD) for how commit messages should be structured. diff --git a/action.yml b/action.yml index 030357d..cfdc42c 100644 --- a/action.yml +++ b/action.yml @@ -18,6 +18,10 @@ inputs: description: filter pulls by base branch name required: false default: all + hard-failure: + description: boolean, if true, fails the build on any error. If false, throws an warning instead. + required: false + runs: using: 'node12' main: 'dist/index.js' diff --git a/dist/index.js b/dist/index.js index a19f725..22aaee5 100644 --- a/dist/index.js +++ b/dist/index.js @@ -2643,6 +2643,7 @@ const DEFAULT_REPOSITORY_NAME = process.env.REPOSITORY_NAME const DEFAULT_LABEL_ACTION = process.env.LABEL_ACTION const DEFAULT_LABEL = process.env.LABEL const DEFAULT_BASE_BRANCH = process.env.BASE_BRANCH +const DEFAULT_HARD_FAILURE = process.env.HARD_FAILURE || 'false' module.exports = { DEFAULT_GITHUB_TOKEN, @@ -2650,6 +2651,7 @@ module.exports = { DEFAULT_LABEL_ACTION, DEFAULT_REPOSITORY_NAME, DEFAULT_BASE_BRANCH, + DEFAULT_HARD_FAILURE, } @@ -5455,7 +5457,14 @@ module.exports = resolveCommand; const core = __webpack_require__(470) -const { DEFAULT_GITHUB_TOKEN, DEFAULT_LABEL, DEFAULT_LABEL_ACTION, DEFAULT_REPOSITORY_NAME, DEFAULT_BASE_BRANCH } = __webpack_require__(328) +const { + DEFAULT_GITHUB_TOKEN, + DEFAULT_LABEL, + DEFAULT_LABEL_ACTION, + DEFAULT_REPOSITORY_NAME, + DEFAULT_BASE_BRANCH, + DEFAULT_HARD_FAILURE, +} = __webpack_require__(328) /** * Gets github token and parses it @@ -5503,17 +5512,45 @@ const getBaseBranch = () => { return (core.getInput('base-branch') || DEFAULT_BASE_BRANCH) } +/** + * Gets hard-failure + */ +const getHardFailure = () => { + const shouldHardFailure = core.getInput('hard-failure') || DEFAULT_HARD_FAILURE + if (shouldHardFailure.toLowerCase() === 'true') return true + return false +} + /** * Sets the Github Action to fail - * @param {String} message + * @param {string} message */ const throwGithubError = (message) => { core.setFailed(message) } +/** + * If app fails outputs a Warning or either throws an Error depending on hard-failure env variable + * @param {Object} error + */ +const outputFailure = (error) => { + if (getHardFailure()) { + throwGithubError(error.message) + } else { + throwGithubWarning(error.message) + } +} +/** + * Sets a Github warning in the console + * @param {string} message + */ +const throwGithubWarning = (message) => { + core.warning(message) +} + /** * returns the owner and name of the repo - * @param {String} repositoryNameAndOwner + * @param {string} repositoryNameAndOwner */ const getSeparatedRepositoryNameAndOwner = (repositoryNameAndOwner) => { const splitNameAndOwner = repositoryNameAndOwner.split('/') @@ -5527,7 +5564,10 @@ module.exports = { getLabelAction, getRepositorySlug, getBaseBranch, + getHardFailure, getSeparatedRepositoryNameAndOwner, + outputFailure, + throwGithubWarning, } @@ -6106,10 +6146,10 @@ module.exports = (promise, onFinally) => { /***/ (function(__unusedmodule, __unusedexports, __webpack_require__) { __webpack_require__(63).config() -const { getLabel, throwGithubError, getLabelAction, getBaseBranch } = __webpack_require__(501) +const { getLabel, outputFailure, getLabelAction, getBaseBranch } = __webpack_require__(501) const GithubAPI = __webpack_require__(880) -const aGithubAPI = new GithubAPI() +let aGithubAPI = {} /** * Adds a label in a PullRequest @@ -6118,6 +6158,7 @@ const aGithubAPI = new GithubAPI() * @param {String} number of the pull request */ const addLabel = (labelToAdd, labels, number) => { + console.log(`...Adding label ${labelToAdd} to PR ${number}`) return aGithubAPI.updatePRLabels(number, [...labels, labelToAdd]) } @@ -6128,6 +6169,7 @@ const addLabel = (labelToAdd, labels, number) => { * @param {String} number of the pull request */ const removeLabel = (labelToDelete, labels, number) => { + console.log(`...Removing label ${labelToDelete} from PR ${number}`) return aGithubAPI.updatePRLabels(number, labels.filter(label => label !== labelToDelete)) } @@ -6141,6 +6183,7 @@ const listAllOpenPRs = (baseBranch) => { const main = async () => { try { + aGithubAPI = new GithubAPI() const openPullRequests = await listAllOpenPRs(getBaseBranch()) for (const pr of openPullRequests) { @@ -6159,7 +6202,7 @@ const main = async () => { } } } catch (error) { - throwGithubError(error.message) + outputFailure(error) } } diff --git a/src/application/index.js b/src/application/index.js index 43e3565..8e638f2 100644 --- a/src/application/index.js +++ b/src/application/index.js @@ -1,8 +1,8 @@ require('dotenv').config() -const { getLabel, throwGithubError, getLabelAction, getBaseBranch } = require('../infrastructure/github-actions') +const { getLabel, outputFailure, getLabelAction, getBaseBranch } = require('../infrastructure/github-actions') const GithubAPI = require('../infrastructure/githubapi') -const aGithubAPI = new GithubAPI() +let aGithubAPI = {} /** * Adds a label in a PullRequest @@ -11,6 +11,7 @@ const aGithubAPI = new GithubAPI() * @param {String} number of the pull request */ const addLabel = (labelToAdd, labels, number) => { + console.log(`...Adding label ${labelToAdd} to PR ${number}`) return aGithubAPI.updatePRLabels(number, [...labels, labelToAdd]) } @@ -21,6 +22,7 @@ const addLabel = (labelToAdd, labels, number) => { * @param {String} number of the pull request */ const removeLabel = (labelToDelete, labels, number) => { + console.log(`...Removing label ${labelToDelete} from PR ${number}`) return aGithubAPI.updatePRLabels(number, labels.filter(label => label !== labelToDelete)) } @@ -34,6 +36,7 @@ const listAllOpenPRs = (baseBranch) => { const main = async () => { try { + aGithubAPI = new GithubAPI() const openPullRequests = await listAllOpenPRs(getBaseBranch()) for (const pr of openPullRequests) { @@ -52,7 +55,7 @@ const main = async () => { } } } catch (error) { - throwGithubError(error.message) + outputFailure(error) } } diff --git a/src/infrastructure/constants.js b/src/infrastructure/constants.js index 566103c..6bd1f74 100644 --- a/src/infrastructure/constants.js +++ b/src/infrastructure/constants.js @@ -3,6 +3,7 @@ const DEFAULT_REPOSITORY_NAME = process.env.REPOSITORY_NAME const DEFAULT_LABEL_ACTION = process.env.LABEL_ACTION const DEFAULT_LABEL = process.env.LABEL const DEFAULT_BASE_BRANCH = process.env.BASE_BRANCH +const DEFAULT_HARD_FAILURE = process.env.HARD_FAILURE || 'false' module.exports = { DEFAULT_GITHUB_TOKEN, @@ -10,4 +11,5 @@ module.exports = { DEFAULT_LABEL_ACTION, DEFAULT_REPOSITORY_NAME, DEFAULT_BASE_BRANCH, + DEFAULT_HARD_FAILURE, } diff --git a/src/infrastructure/github-actions.js b/src/infrastructure/github-actions.js index a44382d..7f36d36 100644 --- a/src/infrastructure/github-actions.js +++ b/src/infrastructure/github-actions.js @@ -1,6 +1,13 @@ const core = require('@actions/core') -const { DEFAULT_GITHUB_TOKEN, DEFAULT_LABEL, DEFAULT_LABEL_ACTION, DEFAULT_REPOSITORY_NAME, DEFAULT_BASE_BRANCH } = require('./constants') +const { + DEFAULT_GITHUB_TOKEN, + DEFAULT_LABEL, + DEFAULT_LABEL_ACTION, + DEFAULT_REPOSITORY_NAME, + DEFAULT_BASE_BRANCH, + DEFAULT_HARD_FAILURE, +} = require('./constants') /** * Gets github token and parses it @@ -48,6 +55,15 @@ const getBaseBranch = () => { return (core.getInput('base-branch') || DEFAULT_BASE_BRANCH) } +/** + * Gets hard-failure + */ +const getHardFailure = () => { + const shouldHardFailure = core.getInput('hard-failure') || DEFAULT_HARD_FAILURE + if (shouldHardFailure.toLowerCase() === 'true') return true + return false +} + /** * Sets the Github Action to fail * @param {string} message @@ -56,6 +72,25 @@ const throwGithubError = (message) => { core.setFailed(message) } +/** + * If app fails outputs a Warning or either throws an Error depending on hard-failure env variable + * @param {Object} error + */ +const outputFailure = (error) => { + if (getHardFailure()) { + throwGithubError(error.message) + } else { + throwGithubWarning(error.message) + } +} +/** + * Sets a Github warning in the console + * @param {string} message + */ +const throwGithubWarning = (message) => { + core.warning(message) +} + /** * returns the owner and name of the repo * @param {string} repositoryNameAndOwner @@ -72,5 +107,8 @@ module.exports = { getLabelAction, getRepositorySlug, getBaseBranch, + getHardFailure, getSeparatedRepositoryNameAndOwner, + outputFailure, + throwGithubWarning, } diff --git a/src/infrastructure/tests/github-actions.test.js b/src/infrastructure/tests/github-actions.test.js index bc10e7f..6c41d77 100644 --- a/src/infrastructure/tests/github-actions.test.js +++ b/src/infrastructure/tests/github-actions.test.js @@ -116,6 +116,19 @@ describe('getBaseBranch', () => { }) }) +describe('getHardFailure', () => { + beforeEach(() => { + jest.resetModules() + }) + it('should return a the value of HARD_FAILURE env', () => { + jest.mock('../constants', () => ({ DEFAULT_HARD_FAILURE: 'TRUE' })) + + // eslint-disable-next-line global-require + const { getHardFailure } = require('../github-actions') + expect(getHardFailure()).toEqual(true) + }) +}) + describe('throwGithubError', () => { beforeEach(() => { jest.resetModules() @@ -130,6 +143,45 @@ describe('throwGithubError', () => { }) }) +describe('outputFailure', () => { + beforeEach(() => { + jest.resetModules() + }) + it('should throw github error if HARD_FAILURE true', () => { + jest.mock('../constants', () => ({ DEFAULT_HARD_FAILURE: 'true' })) + + // eslint-disable-next-line global-require + const { outputFailure } = require('../github-actions') + // eslint-disable-next-line global-require + const core = require('@actions/core') + outputFailure({ message: 'message' }) + expect(core.setFailed).toHaveBeenCalledWith('message') + }) + it('should throw github warning if HARD_FAILURE false', () => { + jest.mock('../constants', () => ({ DEFAULT_HARD_FAILURE: 'false' })) + // eslint-disable-next-line global-require + const { outputFailure } = require('../github-actions') + // eslint-disable-next-line global-require + const core = require('@actions/core') + outputFailure({ message: 'message' }) + expect(core.warning).toBeCalledWith('message') + }) +}) + +describe('throwGithubWarning', () => { + beforeEach(() => { + jest.resetModules() + }) + it('should throw github warning', () => { + // eslint-disable-next-line global-require + const { throwGithubWarning } = require('../github-actions') + // eslint-disable-next-line global-require + const core = require('@actions/core') + throwGithubWarning('message') + expect(core.warning).toHaveBeenCalledWith('message') + }) +}) + describe('getSeparatedRepositoryNameAndOwner', () => { beforeEach(() => { jest.resetModules()