From 09e653692b00777aa56625751110305223bc5917 Mon Sep 17 00:00:00 2001 From: myarmolinsky Date: Thu, 3 Oct 2024 11:17:19 -0400 Subject: [PATCH] Remove no longer needed references and tests for mixpanel Change-type: patch --- automation/deploy-bin.ts | 215 ---------------------- automation/run.ts | 2 - src/events.ts | 4 - tests/commands/app/create.spec.ts | 1 - tests/commands/build.spec.ts | 2 - tests/commands/deploy.spec.ts | 2 - tests/commands/device/device-move.spec.ts | 1 - tests/commands/device/device.spec.ts | 1 - tests/commands/device/devices.spec.ts | 1 - tests/commands/device/supported.spec.ts | 1 - tests/commands/env/add.spec.ts | 1 - tests/commands/env/envs.spec.ts | 1 - tests/commands/env/rename.spec.ts | 1 - tests/commands/env/rm.spec.ts | 1 - tests/commands/help.spec.ts | 1 - tests/commands/logs.spec.ts | 1 - tests/commands/os/configure.spec.ts | 1 - tests/commands/push.spec.ts | 2 - tests/commands/release.spec.ts | 1 - tests/commands/ssh.spec.ts | 1 - tests/commands/tag/set.spec.ts | 1 - tests/commands/version.spec.ts | 1 - tests/commands/whoami.spec.ts | 1 - tests/deprecation.spec.ts | 1 - tests/nock/balena-api-mock.ts | 5 - 25 files changed, 250 deletions(-) delete mode 100644 automation/deploy-bin.ts diff --git a/automation/deploy-bin.ts b/automation/deploy-bin.ts deleted file mode 100644 index 4a345822..00000000 --- a/automation/deploy-bin.ts +++ /dev/null @@ -1,215 +0,0 @@ -/** - * @license - * Copyright 2019 Balena Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import * as _ from 'lodash'; -import * as semver from 'semver'; -import { Octokit } from '@octokit/rest'; -import { throttling } from '@octokit/plugin-throttling'; - -const { GITHUB_TOKEN } = process.env; - -/** Return a cached Octokit instance, creating a new one as needed. */ -const getOctokit = _.once(function () { - const OctokitConstructor = Octokit.plugin(throttling); - return new OctokitConstructor({ - auth: GITHUB_TOKEN, - throttle: { - onRateLimit: (retryAfter: number, options: any) => { - console.warn( - `Request quota exhausted for request ${options.method} ${options.url}`, - ); - // retries 3 times - if (options.request.retryCount < 3) { - console.log(`Retrying after ${retryAfter} seconds!`); - return true; - } - }, - onAbuseLimit: (_retryAfter: number, options: any) => { - // does not retry, only logs a warning - console.warn( - `Abuse detected for request ${options.method} ${options.url}`, - ); - }, - }, - }); -}); - -/** - * Extract pagination information (current page, total pages, ordinal number) - * from the 'link' response header (example below), using the parse-link-header - * npm package: - * "link": "; rel=\"next\", - * ; rel=\"last\"" - * - * @param response Octokit response object (including response.headers.link) - * @param perPageDefault Default per_page pagination value if missing in URL - * @return Object where 'page' is the current page number (1-based), - * 'pages' is the total number of pages, and 'ordinal' is the ordinal number - * (3rd, 4th, 5th...) of the first item in the current page. - */ -async function getPageNumbers( - response: any, - perPageDefault: number, -): Promise<{ page: number; pages: number; ordinal: number }> { - const res = { page: 1, pages: 1, ordinal: 1 }; - if (!response.headers.link) { - return res; - } - const parse = await import('parse-link-header'); - - const parsed = parse(response.headers.link); - if (parsed == null) { - throw new Error(`Failed to parse link header: '${response.headers.link}'`); - } - let perPage = perPageDefault; - if (parsed.next) { - if (parsed.next.per_page) { - perPage = parseInt(parsed.next.per_page, 10); - } - res.page = parseInt(parsed.next.page!, 10) - 1; - res.pages = parseInt(parsed.last!.page!, 10); - } else { - if (parsed.prev!.per_page) { - perPage = parseInt(parsed.prev!.per_page, 10); - } - res.page = res.pages = parseInt(parsed.prev!.page!, 10) + 1; - } - res.ordinal = (res.page - 1) * perPage + 1; - return res; -} - -/** - * Iterate over every GitHub release in the given owner/repo, check whether - * its tag_name matches against the affectedVersions semver spec, and if so - * replace its release description (body) with the given newDescription value. - * @param owner GitHub repo owner, e.g. 'balena-io' or 'pdcastro' - * @param repo GitHub repo, e.g. 'balena-cli' - * @param affectedVersions Semver spec, e.g. '2.6.1 - 7.10.9 || 8.0.0' - * @param newDescription New release description (body) - * @param editID Short string present in newDescription, e.g. '[AA101]', that - * can be searched to determine whether that release has already been updated. - */ -async function updateGitHubReleaseDescriptions( - owner: string, - repo: string, - affectedVersions: string, - newDescription: string, - editID: string, -) { - const perPage = 30; - const octokit = getOctokit(); - const options = octokit.repos.listReleases.endpoint.merge({ - owner, - repo, - per_page: perPage, - }); - let errCount = 0; - type Release = - import('@octokit/rest').RestEndpointMethodTypes['repos']['listReleases']['response']['data'][0]; - for await (const response of octokit.paginate.iterator(options)) { - const { - page: thisPage, - pages: totalPages, - ordinal, - } = await getPageNumbers(response, perPage); - let i = 0; - for (const cliRelease of response.data) { - const prefix = `[#${ordinal + i++} pg ${thisPage}/${totalPages}]`; - if (!cliRelease.id) { - console.error( - `${prefix} Error: missing release ID (errCount=${++errCount})`, - ); - continue; - } - const skipMsg = `${prefix} skipping release "${cliRelease.tag_name}" (${cliRelease.id})`; - if (cliRelease.draft === true) { - console.info(`${skipMsg}: draft release`); - continue; - } else if (cliRelease.body && cliRelease.body.includes(editID)) { - console.info(`${skipMsg}: already updated`); - continue; - } else if (!semver.satisfies(cliRelease.tag_name, affectedVersions)) { - console.info(`${skipMsg}: outside version range`); - continue; - } else { - const updatedRelease = { - owner, - repo, - release_id: cliRelease.id, - body: newDescription, - }; - let oldBodyPreview = cliRelease.body; - if (oldBodyPreview) { - oldBodyPreview = oldBodyPreview.replace(/\s+/g, ' ').trim(); - if (oldBodyPreview.length > 12) { - oldBodyPreview = oldBodyPreview.substring(0, 9) + '...'; - } - } - console.info( - `${prefix} updating release "${cliRelease.tag_name}" (${cliRelease.id}) old body="${oldBodyPreview}"`, - ); - try { - await octokit.repos.updateRelease(updatedRelease); - } catch (err) { - console.error( - `${skipMsg}: Error: ${err.message} (count=${++errCount})`, - ); - continue; - } - } - } - } -} - -/** - * Add a warning description to CLI releases affected by a mixpanel tracking - * security issue (#1359). This function can be executed "manually" with the - * following command line: - * - * npx ts-node --type-check -P automation/tsconfig.json automation/run.ts fix1359 - */ -export async function updateDescriptionOfReleasesAffectedByIssue1359() { - // Run only on Linux/Node10, instead of all platform/Node combinations. - // (It could have been any other platform, as long as it only runs once.) - if (process.platform !== 'linux' || semver.major(process.version) !== 10) { - return; - } - const owner = 'balena-io'; - const repo = 'balena-cli'; - const affectedVersions = - '2.6.1 - 7.10.9 || 8.0.0 - 8.1.0 || 9.0.0 - 9.15.6 || 10.0.0 - 10.17.5 || 11.0.0 - 11.7.2'; - const editID = '[AA100]'; - let newDescription = ` - Please note: the "login" command in this release is affected by a - security issue fixed in versions - [7.10.10](https://github.com/balena-io/balena-cli/releases/tag/v7.10.10), - [8.1.1](https://github.com/balena-io/balena-cli/releases/tag/v8.1.1), - [9.15.7](https://github.com/balena-io/balena-cli/releases/tag/v9.15.7), - [10.17.6](https://github.com/balena-io/balena-cli/releases/tag/v10.17.6), - [11.7.3](https://github.com/balena-io/balena-cli/releases/tag/v11.7.3) - and later. If you need to use this version, avoid passing your password, - keys or tokens as command-line arguments. ${editID}`; - // remove line breaks and collapse white space - newDescription = newDescription.replace(/\s+/g, ' ').trim(); - await updateGitHubReleaseDescriptions( - owner, - repo, - affectedVersions, - newDescription, - editID, - ); -} diff --git a/automation/run.ts b/automation/run.ts index f8fc0273..b0986f43 100644 --- a/automation/run.ts +++ b/automation/run.ts @@ -24,7 +24,6 @@ import { signFilesForNotarization, testShrinkwrap, } from './build-bin'; -import { updateDescriptionOfReleasesAffectedByIssue1359 } from './deploy-bin'; // DEBUG set to falsy for negative values else is truthy process.env.DEBUG = ['0', 'no', 'false', '', undefined].includes( @@ -54,7 +53,6 @@ async function parse(args?: string[]) { 'sign:binaries': signFilesForNotarization, 'catch-uncommitted': catchUncommitted, 'test-shrinkwrap': testShrinkwrap, - fix1359: updateDescriptionOfReleasesAffectedByIssue1359, }; for (const arg of args) { if (!Object.hasOwn(commands, arg)) { diff --git a/src/events.ts b/src/events.ts index 3aa2826a..aa6dcbed 100644 --- a/src/events.ts +++ b/src/events.ts @@ -59,7 +59,6 @@ export async function trackCommand(commandSignature: string) { }); }); } - // Don't actually call mixpanel.track() while running test cases, or if suppressed if ( !process.env.BALENA_CLI_TEST_TYPE && !process.env.BALENARC_NO_ANALYTICS @@ -75,9 +74,6 @@ export async function trackCommand(commandSignature: string) { const TIMEOUT = 4000; -/** - * Make the event tracking HTTPS request to balenaCloud's '/mixpanel' endpoint. - */ async function sendEvent(balenaUrl: string, event: string, username?: string) { const { default: got } = await import('got'); const trackData = { diff --git a/tests/commands/app/create.spec.ts b/tests/commands/app/create.spec.ts index ef1df249..290b5e37 100644 --- a/tests/commands/app/create.spec.ts +++ b/tests/commands/app/create.spec.ts @@ -36,7 +36,6 @@ describe('balena app create', function () { // Temporarily skipped because of parse/checking order issue with -h it.skip('should print help text with the -h flag', async () => { api.expectGetWhoAmI({ optional: true }); - api.expectGetMixpanel({ optional: true }); const { out, err } = await runCommand('app create -h'); diff --git a/tests/commands/build.spec.ts b/tests/commands/build.spec.ts index ec5400a0..cf503c6b 100644 --- a/tests/commands/build.spec.ts +++ b/tests/commands/build.spec.ts @@ -91,7 +91,6 @@ describe('balena build', function () { api = new BalenaAPIMock(); docker = new DockerMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); docker.expectGetPing(); docker.expectGetVersion({ persist: true }); }); @@ -619,7 +618,6 @@ describe('balena build: project validation', function () { this.beforeEach(() => { api = new BalenaAPIMock(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(() => { diff --git a/tests/commands/deploy.spec.ts b/tests/commands/deploy.spec.ts index b256bea6..cff67b75 100644 --- a/tests/commands/deploy.spec.ts +++ b/tests/commands/deploy.spec.ts @@ -82,7 +82,6 @@ describe('balena deploy', function () { api = new BalenaAPIMock(); docker = new DockerMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); api.expectGetApplication({ expandArchitecture: true }); api.expectGetRelease(); api.expectGetUser(); @@ -515,7 +514,6 @@ describe('balena deploy: project validation', function () { this.beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(() => { diff --git a/tests/commands/device/device-move.spec.ts b/tests/commands/device/device-move.spec.ts index 7acdd2d1..aab0699a 100644 --- a/tests/commands/device/device-move.spec.ts +++ b/tests/commands/device/device-move.spec.ts @@ -25,7 +25,6 @@ describe('balena device move', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/device/device.spec.ts b/tests/commands/device/device.spec.ts index 7cd2c7a5..af6cbb43 100644 --- a/tests/commands/device/device.spec.ts +++ b/tests/commands/device/device.spec.ts @@ -27,7 +27,6 @@ describe('balena device', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/device/devices.spec.ts b/tests/commands/device/devices.spec.ts index 5c0ac5ba..ef2d032b 100644 --- a/tests/commands/device/devices.spec.ts +++ b/tests/commands/device/devices.spec.ts @@ -27,7 +27,6 @@ describe('balena devices', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/device/supported.spec.ts b/tests/commands/device/supported.spec.ts index 037f552c..eec1b379 100644 --- a/tests/commands/device/supported.spec.ts +++ b/tests/commands/device/supported.spec.ts @@ -26,7 +26,6 @@ describe('balena devices supported', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/env/add.spec.ts b/tests/commands/env/add.spec.ts index b8d3d095..c16489ed 100644 --- a/tests/commands/env/add.spec.ts +++ b/tests/commands/env/add.spec.ts @@ -28,7 +28,6 @@ describe('balena env add', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/env/envs.spec.ts b/tests/commands/env/envs.spec.ts index aec9e816..14f2df22 100644 --- a/tests/commands/env/envs.spec.ts +++ b/tests/commands/env/envs.spec.ts @@ -31,7 +31,6 @@ describe('balena envs', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); // Random device UUID used to frustrate _.memoize() in utils/cloud.ts fullUUID = randomBytes(16).toString('hex'); shortUUID = fullUUID.substring(0, 7); diff --git a/tests/commands/env/rename.spec.ts b/tests/commands/env/rename.spec.ts index fa461872..78e3cbb1 100644 --- a/tests/commands/env/rename.spec.ts +++ b/tests/commands/env/rename.spec.ts @@ -26,7 +26,6 @@ describe('balena env rename', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/env/rm.spec.ts b/tests/commands/env/rm.spec.ts index 51b910d4..b4ee159f 100644 --- a/tests/commands/env/rm.spec.ts +++ b/tests/commands/env/rm.spec.ts @@ -26,7 +26,6 @@ describe('balena env rm', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/help.spec.ts b/tests/commands/help.spec.ts index 945c6cad..d129728b 100644 --- a/tests/commands/help.spec.ts +++ b/tests/commands/help.spec.ts @@ -111,7 +111,6 @@ describe.skip('balena help', function () { this.beforeEach(() => { api = new BalenaAPIMock(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(() => { diff --git a/tests/commands/logs.spec.ts b/tests/commands/logs.spec.ts index 2b56b660..64670848 100644 --- a/tests/commands/logs.spec.ts +++ b/tests/commands/logs.spec.ts @@ -31,7 +31,6 @@ describe('balena logs', function () { api = new BalenaAPIMock(); supervisor = new SupervisorMock(); api.expectGetWhoAmI(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(() => { diff --git a/tests/commands/os/configure.spec.ts b/tests/commands/os/configure.spec.ts index 72688fee..e3bc3bd4 100644 --- a/tests/commands/os/configure.spec.ts +++ b/tests/commands/os/configure.spec.ts @@ -35,7 +35,6 @@ if (process.platform !== 'win32') { beforeEach(async () => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); tmpPath = (await tmpNameAsync()) as string; await fs.copyFile('./tests/test-data/dummy.img', tmpPath); }); diff --git a/tests/commands/push.spec.ts b/tests/commands/push.spec.ts index 5a2c4c24..9a40d17c 100644 --- a/tests/commands/push.spec.ts +++ b/tests/commands/push.spec.ts @@ -89,7 +89,6 @@ describe('balena push', function () { api = new BalenaAPIMock(); builder = new BuilderMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); api.expectGetApplication(); }); @@ -518,7 +517,6 @@ describe('balena push: project validation', function () { this.beforeEach(() => { api = new BalenaAPIMock(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(() => { diff --git a/tests/commands/release.spec.ts b/tests/commands/release.spec.ts index f977e950..6f42eba8 100644 --- a/tests/commands/release.spec.ts +++ b/tests/commands/release.spec.ts @@ -26,7 +26,6 @@ describe('balena release', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/ssh.spec.ts b/tests/commands/ssh.spec.ts index f2d05874..37a10e1e 100644 --- a/tests/commands/ssh.spec.ts +++ b/tests/commands/ssh.spec.ts @@ -76,7 +76,6 @@ describe('balena ssh', function () { this.beforeEach(function () { api = new BalenaAPIMock(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(function () { diff --git a/tests/commands/tag/set.spec.ts b/tests/commands/tag/set.spec.ts index 0ed18fde..2c106747 100644 --- a/tests/commands/tag/set.spec.ts +++ b/tests/commands/tag/set.spec.ts @@ -28,7 +28,6 @@ describe('balena tag set', function () { beforeEach(() => { api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); }); afterEach(() => { diff --git a/tests/commands/version.spec.ts b/tests/commands/version.spec.ts index 06cbb696..1cbf6696 100644 --- a/tests/commands/version.spec.ts +++ b/tests/commands/version.spec.ts @@ -30,7 +30,6 @@ describe('balena version', function () { this.beforeEach(() => { api = new BalenaAPIMock(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(() => { diff --git a/tests/commands/whoami.spec.ts b/tests/commands/whoami.spec.ts index 14140d19..958531aa 100644 --- a/tests/commands/whoami.spec.ts +++ b/tests/commands/whoami.spec.ts @@ -24,7 +24,6 @@ describe('balena whoami', function () { this.beforeEach(() => { api = new BalenaAPIMock(); - api.expectGetMixpanel({ optional: true }); }); this.afterEach(async () => { diff --git a/tests/deprecation.spec.ts b/tests/deprecation.spec.ts index f42b128b..d78f8b64 100644 --- a/tests/deprecation.spec.ts +++ b/tests/deprecation.spec.ts @@ -68,7 +68,6 @@ describe('DeprecationChecker', function () { npm = new NpmMock(); api = new BalenaAPIMock(); api.expectGetWhoAmI({ optional: true, persist: true }); - api.expectGetMixpanel({ optional: true }); checker = new DeprecationChecker(packageJSON.version); getStub = sandbox.stub(mockStorage, 'get').withArgs(checker.cacheFile); diff --git a/tests/nock/balena-api-mock.ts b/tests/nock/balena-api-mock.ts index 2dcaee39..add690e9 100644 --- a/tests/nock/balena-api-mock.ts +++ b/tests/nock/balena-api-mock.ts @@ -74,7 +74,6 @@ export class BalenaAPIMock extends NockMock { "vpnEndpoint":"vpn.balena-cloud.com", "registryEndpoint":"registry2.balena-cloud.com", "deltaEndpoint":"https://delta.balena-cloud.com", - "mixpanelToken":"", "apiKey":"nothingtoseehere" }`), ); @@ -465,10 +464,6 @@ export class BalenaAPIMock extends NockMock { public expectWhoAmIFail(opts: ScopeOpts = { optional: true }) { this.optGet('/actor/v1/whoami', opts).reply(401); } - - public expectGetMixpanel(opts: ScopeOpts = {}) { - this.optGet(/^\/mixpanel\/track/, opts).reply(200, {}); - } } const appServiceVarsByService: { [key: string]: any } = {