From 0d8c86f81f157a07dbf776a63c8a34d221f7a4ba Mon Sep 17 00:00:00 2001 From: Mary Marchini Date: Sat, 1 Aug 2020 15:11:57 -0700 Subject: [PATCH 1/4] chore(deps): replace github with @octokit/rest `github` has been renamed to `@octokit/rest`. The version sequence was kept, and the package name is the only breaking change on v14.0.0. Ref: https://github.com/octokit/rest.js/releases/tag/v14.0.0 --- lib/github-client.js | 2 +- package-lock.json | 122 ++++++++++++++----------------------------- package.json | 2 +- 3 files changed, 40 insertions(+), 86 deletions(-) diff --git a/lib/github-client.js b/lib/github-client.js index 76f39443..b91af01f 100644 --- a/lib/github-client.js +++ b/lib/github-client.js @@ -1,6 +1,6 @@ 'use strict' -const GitHub = require('github') +const GitHub = require('@octokit/rest') const githubClient = new GitHub({ version: '3.0.0', diff --git a/package-lock.json b/package-lock.json index 68c91dc3..02c99807 100644 --- a/package-lock.json +++ b/package-lock.json @@ -150,6 +150,34 @@ "to-fast-properties": "^2.0.0" } }, + "@octokit/rest": { + "version": "14.0.9", + "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-14.0.9.tgz", + "integrity": "sha512-irP9phKfTXEZIcW2R+VNCtGHZJrXMWmSYp6RRfFn4BtAqtDRXF5z9JxCEQlAhNBf6X1koNi5k49tIAAAEJNlVQ==", + "requires": { + "before-after-hook": "^1.1.0", + "debug": "^3.1.0", + "is-array-buffer": "^1.0.0", + "is-stream": "^1.1.0", + "lodash": "^4.17.4", + "url-template": "^2.0.8" + }, + "dependencies": { + "debug": { + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", + "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", + "requires": { + "ms": "^2.1.1" + } + }, + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + } + } + }, "@sindresorhus/is": { "version": "0.14.0", "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", @@ -272,14 +300,6 @@ "integrity": "sha512-HJ7CfNHrfJLlNTzIEUTj43LNWGkqpRLxm3YjAlcD0ACydk9XynzYsCBHxut+iqt+1aBXkx9UP/w/ZqMr13XIzg==", "dev": true }, - "agent-base": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", - "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", - "requires": { - "es6-promisify": "^5.0.0" - } - }, "ajv": { "version": "6.10.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", @@ -532,6 +552,11 @@ "tweetnacl": "^0.14.3" } }, + "before-after-hook": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-1.4.0.tgz", + "integrity": "sha512-l5r9ir56nda3qu14nAXIlyq1MmUSs0meCIaFAh8HwkFwP1F8eToOuS3ah2VAHHcY04jaYD7FpJC5JTXHYRbkzg==" + }, "binary-extensions": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.0.0.tgz", @@ -1319,19 +1344,6 @@ "integrity": "sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==", "dev": true }, - "es6-promise": { - "version": "4.2.8", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.8.tgz", - "integrity": "sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==" - }, - "es6-promisify": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", - "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", - "requires": { - "es6-promise": "^4.0.3" - } - }, "escape-goat": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz", @@ -2173,40 +2185,6 @@ "assert-plus": "^1.0.0" } }, - "github": { - "version": "13.1.1", - "resolved": "https://registry.npmjs.org/github/-/github-13.1.1.tgz", - "integrity": "sha512-BpItPaOCuvotnNUGXSSEDkB86eqQ7+k7j8/+lu5gbRmNnFPW/uQyFezH1fjy7XojieVNzD/+MgPhBngaw+Ocfw==", - "requires": { - "debug": "^3.1.0", - "dotenv": "^4.0.0", - "https-proxy-agent": "^2.1.0", - "is-stream": "^1.1.0", - "lodash": "^4.17.4", - "proxy-from-env": "^1.0.0", - "url-template": "^2.0.8" - }, - "dependencies": { - "debug": { - "version": "3.2.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", - "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", - "requires": { - "ms": "^2.1.1" - } - }, - "dotenv": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-4.0.0.tgz", - "integrity": "sha1-hk7xN5rO1Vzm+V3r7NzhefegzR0=" - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" - } - } - }, "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", @@ -2375,30 +2353,6 @@ "sshpk": "^1.7.0" } }, - "https-proxy-agent": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", - "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", - "requires": { - "agent-base": "^4.3.0", - "debug": "^3.1.0" - }, - "dependencies": { - "debug": { - "version": "3.2.6", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", - "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", - "requires": { - "ms": "^2.1.1" - } - }, - "ms": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" - } - } - }, "iconv-lite": { "version": "0.4.23", "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", @@ -2477,6 +2431,11 @@ "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" }, + "is-array-buffer": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-1.0.1.tgz", + "integrity": "sha512-lj035IqdAwsodoRGs9/8+Kn3HPoz9CTuZbcw63afugWonxigvUVeHY5d6Ve1O+s1N3RCk7txo2TIWQLbU0SuNA==" + }, "is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", @@ -3877,11 +3836,6 @@ "ipaddr.js": "1.6.0" } }, - "proxy-from-env": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", - "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" - }, "proxyquire": { "version": "1.8.0", "resolved": "https://registry.npmjs.org/proxyquire/-/proxyquire-1.8.0.tgz", diff --git a/package.json b/package.json index 5ced5e94..e2232eaf 100644 --- a/package.json +++ b/package.json @@ -13,6 +13,7 @@ "private": true, "license": "MIT", "dependencies": { + "@octokit/rest": "^14.0.9", "async": "2.1.5", "basic-auth": "^1.0.4", "body-parser": "^1.15.0", @@ -22,7 +23,6 @@ "dotenv": "^2.0.0", "events-async": "^1.2.1", "express": "^4.13.4", - "github": "^13.1.1", "glob": "^7.0.3", "lru-cache": "^4.0.1", "request": "^2.88.0" From a104ceaca4bc7df832c1f67eef7611472ef8638c Mon Sep 17 00:00:00 2001 From: Mary Marchini Date: Sat, 1 Aug 2020 15:16:18 -0700 Subject: [PATCH 2/4] chore(deps): bump @octokit/rest to v15 Only breaking change on v15.0.1 is to `DELETE` calls, which we don't use. Ref: https://github.com/octokit/rest.js/releases/tag/v15.0.1 --- package-lock.json | 193 ++++++++++++++++++++++++++++++++++++++++------ package.json | 2 +- 2 files changed, 169 insertions(+), 26 deletions(-) diff --git a/package-lock.json b/package-lock.json index 02c99807..8decdf91 100644 --- a/package-lock.json +++ b/package-lock.json @@ -151,15 +151,18 @@ } }, "@octokit/rest": { - "version": "14.0.9", - "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-14.0.9.tgz", - "integrity": "sha512-irP9phKfTXEZIcW2R+VNCtGHZJrXMWmSYp6RRfFn4BtAqtDRXF5z9JxCEQlAhNBf6X1koNi5k49tIAAAEJNlVQ==", + "version": "15.18.3", + "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-15.18.3.tgz", + "integrity": "sha512-oHABAvvC83tPIuvUfWRaw9eLThFrCxBgywl+KvEwfTFjoCrMOfEaMh0r39+Ub/EEbV345GJiMzN+zPZ4kqOvbA==", "requires": { "before-after-hook": "^1.1.0", + "btoa-lite": "^1.0.0", "debug": "^3.1.0", - "is-array-buffer": "^1.0.0", - "is-stream": "^1.1.0", + "http-proxy-agent": "^2.1.0", + "https-proxy-agent": "^2.2.0", "lodash": "^4.17.4", + "node-fetch": "^2.1.1", + "universal-user-agent": "^2.0.0", "url-template": "^2.0.8" }, "dependencies": { @@ -300,6 +303,14 @@ "integrity": "sha512-HJ7CfNHrfJLlNTzIEUTj43LNWGkqpRLxm3YjAlcD0ACydk9XynzYsCBHxut+iqt+1aBXkx9UP/w/ZqMr13XIzg==", "dev": true }, + "agent-base": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz", + "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==", + "requires": { + "es6-promisify": "^5.0.0" + } + }, "ajv": { "version": "6.10.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", @@ -716,6 +727,11 @@ "integrity": "sha512-9o5UecI3GhkpM6DrXr69PblIuWxPKk9Y0jHBRhdocZ2y7YECBFCsHm79Pr3OyR2AvjhDkabFJaDJMYRazHgsow==", "dev": true }, + "btoa-lite": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/btoa-lite/-/btoa-lite-1.0.0.tgz", + "integrity": "sha1-M3dm2hWAEhD92VbCLpxokaudAzc=" + }, "buffer-from": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", @@ -1104,6 +1120,25 @@ } } }, + "cross-spawn": { + "version": "6.0.5", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", + "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", + "requires": { + "nice-try": "^1.0.4", + "path-key": "^2.0.1", + "semver": "^5.5.0", + "shebang-command": "^1.2.0", + "which": "^1.2.9" + }, + "dependencies": { + "semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==" + } + } + }, "crypto-random-string": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-2.0.0.tgz", @@ -1299,7 +1334,6 @@ "version": "1.4.4", "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", - "dev": true, "requires": { "once": "^1.4.0" } @@ -1344,6 +1378,19 @@ "integrity": "sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==", "dev": true }, + "es6-promise": { + "version": "4.2.8", + "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.8.tgz", + "integrity": "sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==" + }, + "es6-promisify": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", + "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", + "requires": { + "es6-promise": "^4.0.3" + } + }, "escape-goat": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/escape-goat/-/escape-goat-2.1.1.tgz", @@ -1694,6 +1741,20 @@ "original": "^1.0.0" } }, + "execa": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/execa/-/execa-1.0.0.tgz", + "integrity": "sha512-adbxcyWV46qiHyvSp50TKt05tB4tK3HcmF7/nxfAdhnox83seTDbwnaqKO4sXRy7roHAIFqJP/Rw/AuEbX61LA==", + "requires": { + "cross-spawn": "^6.0.0", + "get-stream": "^4.0.0", + "is-stream": "^1.1.0", + "npm-run-path": "^2.0.0", + "p-finally": "^1.0.0", + "signal-exit": "^3.0.0", + "strip-eof": "^1.0.0" + } + }, "express": { "version": "4.16.3", "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", @@ -2172,7 +2233,6 @@ "version": "4.1.0", "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", - "dev": true, "requires": { "pump": "^3.0.0" } @@ -2343,6 +2403,25 @@ "statuses": ">= 1.4.0 < 2" } }, + "http-proxy-agent": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-2.1.0.tgz", + "integrity": "sha512-qwHbBLV7WviBl0rQsOzH6o5lwyOIvwp/BdFnvVxXORldu5TmjFfjzBcWUWS5kWAZhmv+JtiDhSuQCp4sBfbIgg==", + "requires": { + "agent-base": "4", + "debug": "3.1.0" + }, + "dependencies": { + "debug": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", + "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "requires": { + "ms": "2.0.0" + } + } + } + }, "http-signature": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", @@ -2353,6 +2432,30 @@ "sshpk": "^1.7.0" } }, + "https-proxy-agent": { + "version": "2.2.4", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz", + "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==", + "requires": { + "agent-base": "^4.3.0", + "debug": "^3.1.0" + }, + "dependencies": { + "debug": { + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", + "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", + "requires": { + "ms": "^2.1.1" + } + }, + "ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + } + } + }, "iconv-lite": { "version": "0.4.23", "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", @@ -2431,11 +2534,6 @@ "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" }, - "is-array-buffer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-1.0.1.tgz", - "integrity": "sha512-lj035IqdAwsodoRGs9/8+Kn3HPoz9CTuZbcw63afugWonxigvUVeHY5d6Ve1O+s1N3RCk7txo2TIWQLbU0SuNA==" - }, "is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", @@ -2588,8 +2686,7 @@ "isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", - "dev": true + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" }, "isstream": { "version": "0.1.2", @@ -3019,6 +3116,11 @@ "yallist": "^2.1.2" } }, + "macos-release": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/macos-release/-/macos-release-2.4.1.tgz", + "integrity": "sha512-H/QHeBIN1fIGJX517pvK8IEK53yQOW7YcEI55oYtgjDdoCQQz7eJS94qt5kNrscReEyuD/JcdFCm2XBEcGOITg==" + }, "make-dir": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", @@ -3200,8 +3302,7 @@ "nice-try": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.5.tgz", - "integrity": "sha512-1nh45deeb5olNY7eX82BkPO7SSxR5SSYJiPTrTdFUVYwAl8CKMA5N9PjTYkHiRjisVcxcQ1HXdLhx2qxxJzLNQ==", - "dev": true + "integrity": "sha512-1nh45deeb5olNY7eX82BkPO7SSxR5SSYJiPTrTdFUVYwAl8CKMA5N9PjTYkHiRjisVcxcQ1HXdLhx2qxxJzLNQ==" }, "nock": { "version": "12.0.3", @@ -3232,6 +3333,11 @@ } } }, + "node-fetch": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.0.tgz", + "integrity": "sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA==" + }, "node-modules-regexp": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/node-modules-regexp/-/node-modules-regexp-1.0.0.tgz", @@ -3332,6 +3438,14 @@ "integrity": "sha512-2s47yzUxdexf1OhyRi4Em83iQk0aPvwTddtFz4hnSSw9dCEsLEGf6SwIO8ss/19S9iBb5sJaOuTvTGDeZI00BQ==", "dev": true }, + "npm-run-path": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", + "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "requires": { + "path-key": "^2.0.0" + } + }, "number-is-nan": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", @@ -3544,6 +3658,15 @@ "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", "dev": true }, + "os-name": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/os-name/-/os-name-3.1.0.tgz", + "integrity": "sha512-h8L+8aNjNcMpo/mAIBPn5PXCM16iyPGjHNWo6U1YO8sJTMHtEtyczI6QJnLoplswm6goopQkqc7OAnjhWcugVg==", + "requires": { + "macos-release": "^2.2.0", + "windows-release": "^3.1.0" + } + }, "os-tmpdir": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", @@ -3571,6 +3694,11 @@ "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==", "dev": true }, + "p-finally": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" + }, "p-limit": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", @@ -3669,8 +3797,7 @@ "path-key": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", - "dev": true + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" }, "path-parse": { "version": "1.0.6", @@ -3867,7 +3994,6 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", - "dev": true, "requires": { "end-of-stream": "^1.1.0", "once": "^1.3.1" @@ -4284,7 +4410,6 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", - "dev": true, "requires": { "shebang-regex": "^1.0.0" } @@ -4292,14 +4417,12 @@ "shebang-regex": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", - "dev": true + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" }, "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", - "dev": true + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" }, "sinon": { "version": "1.17.7", @@ -4521,6 +4644,11 @@ "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", "dev": true }, + "strip-eof": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" + }, "strip-json-comments": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", @@ -6109,6 +6237,14 @@ "crypto-random-string": "^2.0.0" } }, + "universal-user-agent": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-2.1.0.tgz", + "integrity": "sha512-8itiX7G05Tu3mGDTdNY2fB4KJ8MgZLS54RdG6PkkfwMAavrXu1mV/lls/GABx9O3Rw4PnTtasxrvbMQoBYY92Q==", + "requires": { + "os-name": "^3.0.0" + } + }, "unpipe": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", @@ -6286,7 +6422,6 @@ "version": "1.3.1", "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", - "dev": true, "requires": { "isexe": "^2.0.0" } @@ -6346,6 +6481,14 @@ } } }, + "windows-release": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-3.3.1.tgz", + "integrity": "sha512-Pngk/RDCaI/DkuHPlGTdIkDiTAnAkyMjoQMZqRsxydNl1qGXNIoZrB7RK8g53F2tEgQBMqQJHQdYZuQEEAu54A==", + "requires": { + "execa": "^1.0.0" + } + }, "wordwrap": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", diff --git a/package.json b/package.json index e2232eaf..1f5d2364 100644 --- a/package.json +++ b/package.json @@ -13,7 +13,7 @@ "private": true, "license": "MIT", "dependencies": { - "@octokit/rest": "^14.0.9", + "@octokit/rest": "^15.18.3", "async": "2.1.5", "basic-auth": "^1.0.4", "body-parser": "^1.15.0", From b7b027a51528cc621e571e68e74f1318bc0c3cff Mon Sep 17 00:00:00 2001 From: Mary Marchini Date: Sun, 2 Aug 2020 15:39:50 -0700 Subject: [PATCH 3/4] chore(jenkins): refactor jenkins-status using events --- app.js | 1 + lib/jenkins-events.js | 79 ++++++++++++++++ scripts/jenkins-status.js | 96 +++++--------------- test/integration/push-jenkins-update.test.js | 74 +++++++++------ 4 files changed, 152 insertions(+), 98 deletions(-) create mode 100644 lib/jenkins-events.js diff --git a/app.js b/app.js index b0b2308d..c5c496f4 100644 --- a/app.js +++ b/app.js @@ -30,6 +30,7 @@ app.use(bunyanMiddleware({ })) require('./lib/github-events')(app, events) +require('./lib/jenkins-events')(app, events) app.use(function logUnhandledErrors (err, req, res, next) { logger.error(err, 'Unhandled error while responding to incoming HTTP request') diff --git a/lib/jenkins-events.js b/lib/jenkins-events.js new file mode 100644 index 00000000..d46991c8 --- /dev/null +++ b/lib/jenkins-events.js @@ -0,0 +1,79 @@ +'use strict' + +const pushJenkinsUpdate = require('../lib/push-jenkins-update') + +const debug = require('debug')('jenkins-events') +const enabledRepos = ['citgm', 'http-parser', 'node', 'node-auto-test'] + +const listOfKnownJenkinsIps = process.env.JENKINS_WORKER_IPS ? process.env.JENKINS_WORKER_IPS.split(',') : [] + +function isKnownJenkinsIp (req) { + const ip = req.connection.remoteAddress.split(':').pop() + + if (listOfKnownJenkinsIps.length && !listOfKnownJenkinsIps.includes(ip)) { + req.log.warn({ ip }, 'Ignoring, not allowed to push Jenkins updates') + return false + } + + return true +} + +function isRelatedToPullRequest (gitRef) { + // refs/pull/12345/head vs refs/heads/v8.x-staging/head + return gitRef.includes('/pull/') +} + +module.exports = (app, events) => { + app.post('/:repo/jenkins/:event', async (req, res) => { + const isValid = pushJenkinsUpdate.validate(req.body) + const repo = req.params.repo + const event = req.params.event + const owner = req.body.owner || process.env.JENKINS_DEFAULT_GH_OWNER || 'nodejs' + + if (!isValid) { + return res.status(400).end('Invalid payload') + } + + if (!isRelatedToPullRequest(req.body.ref)) { + return res.status(400).end('Will only push builds related to pull requests') + } + + if (!enabledRepos.includes(repo)) { + return res.status(400).end('Invalid repository') + } + + if (!isKnownJenkinsIp(req)) { + return res.status(401).end('Invalid Jenkins IP') + } + + const data = { + ...req.body, + owner, + repo, + event + } + + try { + await app.emitJenkinsEvent(event, data, req.log) + res.status(200) + } catch (err) { + req.log.error(err, 'Error while emitting Jenkins event') + res.status(500) + } + + res.end() + }) + + app.emitJenkinsEvent = function emitJenkinsEvent (event, data, logger) { + const { identifier } = data + + // create unique logger which is easily traceable throughout the entire app + // by having e.g. "nodejs/nodejs.org/#1337" part of every subsequent log statement + data.logger = logger.child({ identifier, event }, true) + + data.logger.info('Emitting Jenkins event') + debug(data) + + return events.emit(`jenkins.${event}`, data) + } +} diff --git a/scripts/jenkins-status.js b/scripts/jenkins-status.js index 9b307fae..f9feaf0a 100644 --- a/scripts/jenkins-status.js +++ b/scripts/jenkins-status.js @@ -1,84 +1,36 @@ 'use strict' const pushJenkinsUpdate = require('../lib/push-jenkins-update') -const enabledRepos = ['citgm', 'http-parser', 'node'] -const jenkinsIpWhitelist = process.env.JENKINS_WORKER_IPS ? process.env.JENKINS_WORKER_IPS.split(',') : [] +function handleJenkinsStart (event) { + const { repo, owner } = event -function isJenkinsIpWhitelisted (req) { - const ip = req.connection.remoteAddress.split(':').pop() - - if (jenkinsIpWhitelist.length && !jenkinsIpWhitelist.includes(ip)) { - req.log.warn({ ip }, 'Ignoring, not allowed to push Jenkins updates') - return false - } - - return true -} - -function isRelatedToPullRequest (gitRef) { - // refs/pull/12345/head vs refs/heads/v8.x-staging/head - return gitRef.includes('/pull/') -} - -module.exports = function (app) { - app.post('/:repo/jenkins/start', (req, res) => { - const isValid = pushJenkinsUpdate.validate(req.body) - const repo = req.params.repo - - if (!isValid) { - return res.status(400).end('Invalid payload') - } - - if (!isRelatedToPullRequest(req.body.ref)) { - return res.status(400).end('Will only push builds related to pull requests') - } - - if (!enabledRepos.includes(repo)) { - return res.status(400).end('Invalid repository') - } - - if (!isJenkinsIpWhitelisted(req)) { - return res.status(401).end('Invalid Jenkins IP') + pushJenkinsUpdate.pushStarted({ + owner, + repo, + logger: event.logger + }, event, (err) => { + if (err) { + event.logger.error(err, 'Error while handling Jenkins start event') } - - pushJenkinsUpdate.pushStarted({ - owner: 'nodejs', - repo, - logger: req.log - }, req.body, (err) => { - const statusCode = err !== null ? 500 : 201 - res.status(statusCode).end() - }) }) +} - app.post('/:repo/jenkins/end', (req, res) => { - const isValid = pushJenkinsUpdate.validate(req.body) - const repo = req.params.repo - - if (!isValid) { - return res.status(400).end('Invalid payload') - } - - if (!isRelatedToPullRequest(req.body.ref)) { - return res.status(400).end('Will only push builds related to pull requests') - } - - if (!enabledRepos.includes(repo)) { - return res.status(400).end('Invalid repository') - } +function handleJenkinsStop (event) { + const { repo, owner } = event - if (!isJenkinsIpWhitelisted(req)) { - return res.status(401).end('Invalid Jenkins IP') + pushJenkinsUpdate.pushEnded({ + owner, + repo, + logger: event.logger + }, event, (err) => { + if (err) { + event.logger.error(err, 'Error while handling Jenkins end event') } - - pushJenkinsUpdate.pushEnded({ - owner: 'nodejs', - repo, - logger: req.log - }, req.body, (err) => { - const statusCode = err !== null ? 500 : 201 - res.status(statusCode).end() - }) }) } + +module.exports = function (_, event) { + event.on('jenkins.start', handleJenkinsStart) + event.on('jenkins.end', handleJenkinsStop) +} diff --git a/test/integration/push-jenkins-update.test.js b/test/integration/push-jenkins-update.test.js index ee3a66bf..aea41ab8 100644 --- a/test/integration/push-jenkins-update.test.js +++ b/test/integration/push-jenkins-update.test.js @@ -14,21 +14,25 @@ require('../../scripts/jenkins-status')(app, events) tap.test('Sends POST requests to https://api.github.com/repos/nodejs/node/statuses/', (t) => { const jenkinsPayload = readFixture('success-payload.json') - const prCommitsScope = setupGetCommitsMock('node') - const scope = nock('https://api.github.com') + setupGetCommitsMock('node') + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) + nock('https://api.github.com') .filteringPath(ignoreQueryParams) .post('/repos/nodejs/node/statuses/8a5fec2a6bade91e544a30314d7cf21f8a200de1') .reply(201) + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) - t.plan(1) + t.plan(3) supertest(app) .post('/node/jenkins/start') .send(jenkinsPayload) - .expect(201) + .expect(200) .end((err, res) => { - prCommitsScope.done() - scope.done() t.equal(err, null) }) }) @@ -36,21 +40,27 @@ tap.test('Sends POST requests to https://api.github.com/repos/nodejs/node/status tap.test('Allows repository name to be provided with URL parameter when pushing job started', (t) => { const jenkinsPayload = readFixture('pending-payload.json') - const prCommitsScope = setupGetCommitsMock('citgm') - const scope = nock('https://api.github.com') + setupGetCommitsMock('citgm') + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) + nock('https://api.github.com') .filteringPath(ignoreQueryParams) .post('/repos/nodejs/citgm/statuses/8a5fec2a6bade91e544a30314d7cf21f8a200de1') .reply(201) + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) - t.plan(1) + t.plan(3) supertest(app) .post('/citgm/jenkins/start') .send(jenkinsPayload) - .expect(201) + .expect(200) .end((err, res) => { - prCommitsScope.done() - scope.done() + // prCommitsScope.done() + // scope.done() t.equal(err, null) }) }) @@ -58,21 +68,27 @@ tap.test('Allows repository name to be provided with URL parameter when pushing tap.test('Allows repository name to be provided with URL parameter when pushing job ended', (t) => { const jenkinsPayload = readFixture('success-payload.json') - const prCommitsScope = setupGetCommitsMock('citgm') - const scope = nock('https://api.github.com') + setupGetCommitsMock('citgm') + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) + nock('https://api.github.com') .filteringPath(ignoreQueryParams) .post('/repos/nodejs/citgm/statuses/8a5fec2a6bade91e544a30314d7cf21f8a200de1') .reply(201) + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) - t.plan(1) + t.plan(3) supertest(app) .post('/citgm/jenkins/end') .send(jenkinsPayload) - .expect(201) + .expect(200) .end((err, res) => { - prCommitsScope.done() - scope.done() + // prCommitsScope.done() + // scope.done() t.equal(err, null) }) }) @@ -80,8 +96,11 @@ tap.test('Allows repository name to be provided with URL parameter when pushing tap.test('Forwards payload provided in incoming POST to GitHub status API', (t) => { const fixture = readFixture('success-payload.json') - const prCommitsScope = setupGetCommitsMock('node') - const scope = nock('https://api.github.com') + setupGetCommitsMock('node') + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) + nock('https://api.github.com') .filteringPath(ignoreQueryParams) .post('/repos/nodejs/node/statuses/8a5fec2a6bade91e544a30314d7cf21f8a200de1', { state: 'success', @@ -90,16 +109,19 @@ tap.test('Forwards payload provided in incoming POST to GitHub status API', (t) target_url: 'https://ci.nodejs.org/job/node-test-commit-osx/3157/' }) .reply(201) + .on('replied', (req, interceptor) => { + t.doesNotThrow(() => interceptor.scope.done()) + }) - t.plan(1) + t.plan(3) supertest(app) .post('/node/jenkins/start') .send(fixture) - .expect(201) + .expect(200) .end((err, res) => { - prCommitsScope.done() - scope.done() + // prCommitsScope.done() + // scope.done() t.equal(err, null) }) }) @@ -123,7 +145,7 @@ tap.test('Posts a CI comment in the related PR when Jenkins build is named node- supertest(app) .post('/node/jenkins/start') .send(fixture) - .expect(201) + .expect(200) .end((err, res) => { commentScope.done() t.equal(err, null) @@ -151,7 +173,7 @@ tap.test('Posts a CI comment in the related PR when Jenkins build is named node- supertest(app) .post('/node/jenkins/start') .send(fixture) - .expect(201) + .expect(200) .end((err, res) => { commentScope.done() t.equal(err, null) From 4907f69e6311cb75b774f9faba12c2486125dded Mon Sep 17 00:00:00 2001 From: Mary Marchini Date: Sun, 2 Aug 2020 16:27:18 -0700 Subject: [PATCH 4/4] feat: relay jenkins and gh events to gh --- lib/github-events.js | 1 + lib/jenkins-events.js | 5 ++++- scripts/event-relay.js | 44 ++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 49 insertions(+), 1 deletion(-) create mode 100644 scripts/event-relay.js diff --git a/lib/github-events.js b/lib/github-events.js index 00523af1..3152f430 100644 --- a/lib/github-events.js +++ b/lib/github-events.js @@ -51,6 +51,7 @@ module.exports = (app, events) => { data.logger.info('Emitting GitHub event') debug(data) + events.emit('github', data, org, repo, data.sender.login) return events.emit(data.action, data, org, repo, data.sender.login) } } diff --git a/lib/jenkins-events.js b/lib/jenkins-events.js index d46991c8..a57cff19 100644 --- a/lib/jenkins-events.js +++ b/lib/jenkins-events.js @@ -3,7 +3,9 @@ const pushJenkinsUpdate = require('../lib/push-jenkins-update') const debug = require('debug')('jenkins-events') -const enabledRepos = ['citgm', 'http-parser', 'node', 'node-auto-test'] +const enabledRepos = process.env.JENKINS_ENABLED_REPOS + ? process.env.JENKINS_ENABLED_REPOS.split(',') + : ['citgm', 'http-parser', 'node', 'node-auto-test'] const listOfKnownJenkinsIps = process.env.JENKINS_WORKER_IPS ? process.env.JENKINS_WORKER_IPS.split(',') : [] @@ -74,6 +76,7 @@ module.exports = (app, events) => { data.logger.info('Emitting Jenkins event') debug(data) + events.emit(`jenkins`, data) return events.emit(`jenkins.${event}`, data) } } diff --git a/scripts/event-relay.js b/scripts/event-relay.js new file mode 100644 index 00000000..fa3acee6 --- /dev/null +++ b/scripts/event-relay.js @@ -0,0 +1,44 @@ +'use strict' + +const githubClient = require('../lib/github-client') + +async function handleJenkinsRelay (event) { + const { owner, repo, identifier } = event + const eventType = `jenkins.${identifier}.${event.event}` + try { + event.logger.debug(`Relaying ${eventType} to ${owner}/${repo}`) + await githubClient.repos.createDispatchEvent({ + owner, + repo, + event_type: eventType, + client_payload: event + }) + return true + } catch (err) { + event.logger.error(err, `Failed to relay ${eventType} to ${owner}/${repo}`) + return false + } +} + +async function handleGitHubRelay (event, owner, repo) { + const { action } = event + const eventType = `github.${action}` + try { + event.logger.debug(`Relaying ${eventType} to ${owner}/${repo}`) + await githubClient.repos.createDispatchEvent({ + owner, + repo, + event_type: eventType, + client_payload: event + }) + return true + } catch (err) { + event.logger.error(err, `Failed to relay ${eventType} to ${owner}/${repo}`) + return false + } +} + +module.exports = function (_, event) { + event.on('jenkins', handleJenkinsRelay) + event.on('github', handleGitHubRelay) +}