From c629c84eec30e693fe2f6c4a648e03b4bb8e5953 Mon Sep 17 00:00:00 2001 From: Mathis Wiehl Date: Mon, 30 Jul 2018 18:34:51 +0200 Subject: [PATCH 1/6] test(auth): fix describe title (#965) --- packages/auth/test/commands/auth/token.test.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/auth/test/commands/auth/token.test.ts b/packages/auth/test/commands/auth/token.test.ts index 9f077ae7d6..13b4b0b41c 100644 --- a/packages/auth/test/commands/auth/token.test.ts +++ b/packages/auth/test/commands/auth/token.test.ts @@ -1,6 +1,6 @@ import {expect, test} from '../../test' -describe('auth:whoami', () => { +describe('auth:token', () => { test .env({HEROKU_API_KEY: 'foobar'}) .nock('https://api.heroku.com', api => api From b681eb5452b19aaf6f238a24919864192af58fea Mon Sep 17 00:00:00 2001 From: RasPhilCo Date: Thu, 2 Aug 2018 11:03:33 -0700 Subject: [PATCH 2/6] fix(autocomplete): filepath completions (#968) --- packages/autocomplete/src/commands/autocomplete/create.ts | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/packages/autocomplete/src/commands/autocomplete/create.ts b/packages/autocomplete/src/commands/autocomplete/create.ts index 1878c9b48b..0e48d9def0 100644 --- a/packages/autocomplete/src/commands/autocomplete/create.ts +++ b/packages/autocomplete/src/commands/autocomplete/create.ts @@ -156,9 +156,8 @@ export default class Create extends AutocompleteBase { const hasCompletion = f.hasOwnProperty('completion') || this.findCompletion(flag, id) const name = isBoolean ? flag : `${flag}=-` let cachecompl = '' - if (hasCompletion) { - cachecompl = this.wantsLocalFiles(flag) ? ':_files' : ': :_compadd_flag_options' - } + if (hasCompletion) { cachecompl = ': :_compadd_flag_options' } + if (this.wantsLocalFiles(flag)) { cachecompl = ': :_files' } const help = isBoolean ? '(switch) ' : (hasCompletion ? '(autocomplete) ' : '') const completion = `--${name}[${help}${f.description}]${cachecompl}` return `"${completion}"` From 4328757998ba76b5c9fe80b92c8c09e8c7faf59b Mon Sep 17 00:00:00 2001 From: Michael Friis Date: Fri, 10 Aug 2018 08:25:37 -0700 Subject: [PATCH 3/6] vpn config command should not be hidden (#974) --- packages/spaces/commands/vpn/config.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/spaces/commands/vpn/config.js b/packages/spaces/commands/vpn/config.js index e9c08df9ed..0db241b84a 100644 --- a/packages/spaces/commands/vpn/config.js +++ b/packages/spaces/commands/vpn/config.js @@ -64,7 +64,7 @@ You will use the information provided by this command to establish a Private Spa - The Customer Gateway value is the Public IP of your VPN Gateway - The VPN Gateway must use the IKE Version shown and the Pre-shared Keys as the authentication method `, - hidden: true, + hidden: false, needsApp: false, needsAuth: true, args: [{name: 'name', optional: true, hidden: true}], From df5fa0d615abad90d2c8cf1eb660fe14990efe06 Mon Sep 17 00:00:00 2001 From: Jillian Tullo Date: Fri, 10 Aug 2018 15:31:05 -0400 Subject: [PATCH 4/6] check if the connection is already active before continuing into the waiting loop (#977) --- packages/spaces/commands/vpn/wait.js | 13 +++++++++---- packages/spaces/test/commands/vpn/wait.js | 20 ++++++++++++++++++++ 2 files changed, 29 insertions(+), 4 deletions(-) diff --git a/packages/spaces/commands/vpn/wait.js b/packages/spaces/commands/vpn/wait.js index e329ed6775..251c475f48 100644 --- a/packages/spaces/commands/vpn/wait.js +++ b/packages/spaces/commands/vpn/wait.js @@ -18,15 +18,19 @@ function * run (context, heroku) { const interval = (typeof context.flags.interval !== 'undefined' ? context.flags.interval : 10) * 1000 const timeout = (typeof context.flags.timeout !== 'undefined' ? context.flags.timeout : 20 * 60) * 1000 const deadline = new Date(new Date().getTime() + timeout) + + let lib = require('../../lib/vpn-connections')(heroku) + let info = yield lib.getVPNConnection(space, name) + if (info.status === 'active') { + cli.log('VPN has been allocated.') + return + } + const spinner = new cli.Spinner({text: `Waiting for VPN Connection ${cli.color.green(name)} to allocate...`}) spinner.start() - let lib = require('../../lib/vpn-connections')(heroku) - let info = {} do { - info = yield lib.getVPNConnection(space, name) - if ((new Date()).getTime() >= deadline) { throw new Error('Timeout waiting for VPN to become allocated.') } @@ -36,6 +40,7 @@ function * run (context, heroku) { } yield wait(interval) + info = yield lib.getVPNConnection(space, name) } while (info.status !== 'active') spinner.stop('done\n') diff --git a/packages/spaces/test/commands/vpn/wait.js b/packages/spaces/test/commands/vpn/wait.js index 3374419197..67d4e4890f 100644 --- a/packages/spaces/test/commands/vpn/wait.js +++ b/packages/spaces/test/commands/vpn/wait.js @@ -183,4 +183,24 @@ Tunnel 2 52.44.146.199 52.44.146.198 apresharedkey2 10.0.0.0/16 1 }) .then(() => api.done()) }) + + it('tells the user if the VPN has been allocated', function () { + let api = nock('https://api.heroku.com:443') + .get('/spaces/my-space/vpn-connections/vpn-connection-allocated') + .reply(200, { + id: '123456789012', + name: 'vpn-connection-name-config', + public_ip: '35.161.69.30', + routable_cidrs: [ '172.16.0.0/16' ], + ike_version: 1, + space_cidr_block: '10.0.0.0/16', + status: 'active', + status_message: '' + }) + + return cmd.run({flags: {space: 'my-space', name: 'vpn-connection-allocated', interval: 0}}) + .then(() => expect(cli.stdout).to.equal( + `VPN has been allocated.\n`)) + .then(() => api.done()) + }) }) From 052e0f1ef8854dc80d91a0290d965ecc44d1d1b7 Mon Sep 17 00:00:00 2001 From: Jesse Brown Date: Tue, 14 Aug 2018 09:34:45 -0500 Subject: [PATCH 5/6] Add support for viewing parallel test runs to CI plugin (#980) * Ran oclif plugin and start ci:info * Update dependencies and config - Update tsconfig - Move out utilities * Add color * Update heroku ci interfaces * Update to use latest API schema * Remove variant * Upgrade heroku-cli/schema * ci:info working * Adapt code to ts * Restructure in utils * Add ci:last * Add tests to ci:info * Pulled interfaces from Kolkrabbi schema * WIP migrating ci:run * Move utilities and update dependencies * Use the right host * Add logs back * using cli-ux to show progress and completion * Display of test run works for single and multi-node * Add rerun command * Removing commands in favor of new commands * Fixed up tests * Delete test no longer necessary * Add typed sinon * Add test for run * Added new package to cli, got run command tests working * Adding re-run tests * more tests * Updated readme and updated another test * simplify test * removing try...catch that was making test the error codes harder --- packages/ci-v5/commands/ci/info.js | 39 --- packages/ci-v5/commands/ci/last.js | 40 --- packages/ci-v5/commands/ci/rerun.js | 69 ---- packages/ci-v5/commands/ci/run.js | 58 ---- packages/ci-v5/test/commands/ci/last-test.js | 79 ----- packages/ci/.circleci/config.yml | 65 ++++ packages/ci/.circleci/greenkeeper | 25 ++ packages/ci/.editorconfig | 11 + packages/ci/.gitattributes | 3 + packages/ci/.gitignore | 8 + packages/ci/.nycrc | 12 + packages/ci/LICENSE | 21 ++ packages/ci/README.md | 60 ++++ packages/ci/appveyor.yml | 21 ++ packages/ci/bin/run | 4 + packages/ci/bin/run.cmd | 3 + packages/ci/package.json | 72 +++++ packages/ci/src/commands/ci/info.ts | 32 ++ packages/ci/src/commands/ci/last.ts | 32 ++ packages/ci/src/commands/ci/rerun.ts | 66 ++++ packages/ci/src/commands/ci/run.ts | 53 ++++ packages/ci/src/index.ts | 1 + packages/ci/src/interfaces/kolkrabbi.ts | 312 +++++++++++++++++++ packages/ci/src/utils/git.js | 88 ++++++ packages/ci/src/utils/pipelines.ts | 57 ++++ packages/ci/src/utils/source.ts | 49 +++ packages/ci/src/utils/test-run.ts | 164 ++++++++++ packages/ci/test/commands/ci/info.test.ts | 310 ++++++++++++++++++ packages/ci/test/commands/ci/last.test.ts | 93 ++++++ packages/ci/test/commands/ci/rerun.test.ts | 209 +++++++++++++ packages/ci/test/commands/ci/run.test.ts | 123 ++++++++ packages/ci/test/helpers/init.js | 2 + packages/ci/test/mocha.opts | 7 + packages/ci/test/tsconfig.json | 11 + packages/ci/tsconfig.json | 18 ++ packages/ci/tslint.json | 3 + packages/cli/package.json | 2 + yarn.lock | 150 ++++++++- 38 files changed, 2082 insertions(+), 290 deletions(-) delete mode 100644 packages/ci-v5/commands/ci/info.js delete mode 100644 packages/ci-v5/commands/ci/last.js delete mode 100644 packages/ci-v5/commands/ci/rerun.js delete mode 100644 packages/ci-v5/commands/ci/run.js delete mode 100644 packages/ci-v5/test/commands/ci/last-test.js create mode 100644 packages/ci/.circleci/config.yml create mode 100755 packages/ci/.circleci/greenkeeper create mode 100644 packages/ci/.editorconfig create mode 100644 packages/ci/.gitattributes create mode 100644 packages/ci/.gitignore create mode 100644 packages/ci/.nycrc create mode 100644 packages/ci/LICENSE create mode 100644 packages/ci/README.md create mode 100644 packages/ci/appveyor.yml create mode 100755 packages/ci/bin/run create mode 100644 packages/ci/bin/run.cmd create mode 100644 packages/ci/package.json create mode 100644 packages/ci/src/commands/ci/info.ts create mode 100644 packages/ci/src/commands/ci/last.ts create mode 100644 packages/ci/src/commands/ci/rerun.ts create mode 100644 packages/ci/src/commands/ci/run.ts create mode 100644 packages/ci/src/index.ts create mode 100644 packages/ci/src/interfaces/kolkrabbi.ts create mode 100644 packages/ci/src/utils/git.js create mode 100644 packages/ci/src/utils/pipelines.ts create mode 100644 packages/ci/src/utils/source.ts create mode 100644 packages/ci/src/utils/test-run.ts create mode 100644 packages/ci/test/commands/ci/info.test.ts create mode 100644 packages/ci/test/commands/ci/last.test.ts create mode 100644 packages/ci/test/commands/ci/rerun.test.ts create mode 100644 packages/ci/test/commands/ci/run.test.ts create mode 100644 packages/ci/test/helpers/init.js create mode 100644 packages/ci/test/mocha.opts create mode 100644 packages/ci/test/tsconfig.json create mode 100644 packages/ci/tsconfig.json create mode 100644 packages/ci/tslint.json diff --git a/packages/ci-v5/commands/ci/info.js b/packages/ci-v5/commands/ci/info.js deleted file mode 100644 index 1643230015..0000000000 --- a/packages/ci-v5/commands/ci/info.js +++ /dev/null @@ -1,39 +0,0 @@ -const cli = require('heroku-cli-util') -const co = require('co') -const TestRun = require('../../lib/test-run') -const Utils = require('../../lib/utils') -const PipelineCompletion = require('../../lib/completions') - -function * run (context, heroku) { - const pipeline = yield Utils.getPipeline(context, heroku) - return yield TestRun.displayAndExit(pipeline, context.args.number, { heroku }) -} - -module.exports = { - topic: 'ci', - command: 'info', - wantsApp: true, - needsAuth: true, - args: [ - { - name: 'number', - description: 'the test run number to show' - } - ], - flags: [ - { - name: 'pipeline', - char: 'p', - hasValue: true, - description: 'pipeline', - completion: PipelineCompletion - } - ], - description: 'test run information', - help: `show the status of a specific test run - - Example: - - $ heroku ci:info 1288 --app murmuring-headland-14719`, - run: cli.command(co.wrap(run)) -} diff --git a/packages/ci-v5/commands/ci/last.js b/packages/ci-v5/commands/ci/last.js deleted file mode 100644 index 1ee58a1b5f..0000000000 --- a/packages/ci-v5/commands/ci/last.js +++ /dev/null @@ -1,40 +0,0 @@ -const cli = require('heroku-cli-util') -const co = require('co') -const api = require('../../lib/heroku-api') -const TestRun = require('../../lib/test-run') -const Utils = require('../../lib/utils') -const PipelineCompletion = require('../../lib/completions') - -function * run (context, heroku) { - const pipeline = yield Utils.getPipeline(context, heroku) - const lastRun = yield api.latestTestRun(heroku, pipeline.id) - - if (!lastRun) { - return cli.error('No Heroku CI runs found for this pipeline.') - } - - return yield TestRun.displayAndExit(pipeline, lastRun.number, { heroku }) -} - -module.exports = { - topic: 'ci', - command: 'last', - wantsApp: true, - needsAuth: true, - description: 'get the results of the last run', - flags: [ - { - name: 'pipeline', - char: 'p', - hasValue: true, - description: 'pipeline', - completion: PipelineCompletion - } - ], - help: `looks for the most recent run and returns the output of that run - - Example: - - $ heroku ci:last --app murmuring-headland-14719`, - run: cli.command(co.wrap(run)) -} diff --git a/packages/ci-v5/commands/ci/rerun.js b/packages/ci-v5/commands/ci/rerun.js deleted file mode 100644 index d9fb2fc44f..0000000000 --- a/packages/ci-v5/commands/ci/rerun.js +++ /dev/null @@ -1,69 +0,0 @@ -'use strict' -const cli = require('heroku-cli-util') -const co = require('co') -const api = require('../../lib/heroku-api') -const source = require('../../lib/source') -const TestRun = require('../../lib/test-run') -const Utils = require('../../lib/utils') -const PipelineCompletion = require('../../lib/completions') - -function * run (context, heroku) { - const pipeline = yield Utils.getPipeline(context, heroku) - let sourceTestRun - - if (context.args.number) { - sourceTestRun = yield cli.action(`Fetching test run #${context.args.number}`, co(function * () { - return yield api.testRun(heroku, pipeline.id, context.args.number) - })) - } else { - sourceTestRun = yield cli.action(`Fetching latest test run`, co(function * () { - return yield api.latestTestRun(heroku, pipeline.id) - })) - cli.log(`Rerunning test run #${sourceTestRun.number}...`) - } - - const sourceBlobUrl = yield cli.action('Preparing source', co(function * () { - return yield source.createSourceBlob(sourceTestRun.commit_sha, context, heroku) - })) - - const pipelineRepository = yield api.pipelineRepository(heroku, pipeline.id) - const organization = pipelineRepository.organization && - pipelineRepository.organization.name - - const testRun = yield cli.action('Starting test run', co(function * () { - return yield api.createTestRun(heroku, { - commit_branch: sourceTestRun.commit_branch, - commit_message: sourceTestRun.commit_message, - commit_sha: sourceTestRun.commit_sha, - pipeline: pipeline.id, - organization, - source_blob_url: sourceBlobUrl - }) - })) - - return yield TestRun.displayAndExit(pipeline, testRun.number, { heroku }) -} - -module.exports = { - topic: 'ci', - command: 'rerun', - wantsApp: true, - needsAuth: true, - description: 'rerun tests against current directory', - args: [{ name: 'number', optional: true }], - flags: [ - { - name: 'pipeline', - char: 'p', - hasValue: true, - description: 'pipeline', - completion: PipelineCompletion - } - ], - run: cli.command(co.wrap(run)), - help: `uploads the contents of the current directory, using git archive, to Heroku and runs the tests - - Example: - - $ heroku ci:rerun 985 --app murmuring-headland-14719` -} diff --git a/packages/ci-v5/commands/ci/run.js b/packages/ci-v5/commands/ci/run.js deleted file mode 100644 index acf1ed5d96..0000000000 --- a/packages/ci-v5/commands/ci/run.js +++ /dev/null @@ -1,58 +0,0 @@ -const cli = require('heroku-cli-util') -const co = require('co') -const api = require('../../lib/heroku-api') -const git = require('../../lib/git') -const source = require('../../lib/source') -const TestRun = require('../../lib/test-run') -const Utils = require('../../lib/utils') -const PipelineCompletion = require('../../lib/completions') - -function * run (context, heroku) { - const pipeline = yield Utils.getPipeline(context, heroku) - - const commit = yield git.readCommit('HEAD') - const sourceBlobUrl = yield cli.action('Preparing source', co(function * () { - return yield source.createSourceBlob(commit.ref, context, heroku) - })) - - const pipelineRepository = yield api.pipelineRepository(heroku, pipeline.id) - const organization = pipelineRepository.organization && - pipelineRepository.organization.name - - const testRun = yield cli.action('Starting test run', co(function * () { - return yield api.createTestRun(heroku, { - commit_branch: commit.branch, - commit_message: commit.message, - commit_sha: commit.ref, - pipeline: pipeline.id, - organization, - source_blob_url: sourceBlobUrl - }) - })) - - return yield TestRun.displayAndExit(pipeline, testRun.number, { heroku }) -} - -module.exports = { - topic: 'ci', - command: 'run', - wantsApp: true, - needsAuth: true, - description: 'run tests against current directory', - flags: [ - { - name: 'pipeline', - char: 'p', - hasValue: true, - description: 'pipeline', - completion: PipelineCompletion - } - ], - run: cli.command(co.wrap(run)), - help: `uploads the contents of the current directory to Heroku and runs the tests - - Example: - - $ heroku ci:run --app murmuring-headland-14719` - -} diff --git a/packages/ci-v5/test/commands/ci/last-test.js b/packages/ci-v5/test/commands/ci/last-test.js deleted file mode 100644 index 3f1bb354c5..0000000000 --- a/packages/ci-v5/test/commands/ci/last-test.js +++ /dev/null @@ -1,79 +0,0 @@ -/* eslint-env mocha */ - -const nock = require('nock') -const expect = require('chai').expect -const cli = require('heroku-cli-util') -const sinon = require('sinon') -const cmd = require('../../../commands/ci/last') -const Factory = require('../../lib/factory') - -describe('heroku ci:last', function () { - let testRun, testNode, setupOutput, pipeline, testOutput - - beforeEach(function () { - cli.mockConsole() - sinon.stub(process, 'exit') - - setupOutput = '' - testOutput = '' - pipeline = Factory.pipeline - - testRun = { - id: '123-abc', - number: 123, - pipeline: pipeline, - status: 'succeeded', - commit_sha: '123abc456def', - commit_branch: 'master' - } - - testNode = { - output_stream_url: 'https://output.com/tests', - setup_stream_url: 'https://output.com/setup', - test_run: { id: testRun.id }, - exit_code: 1 - } - }) - - afterEach(function () { - process.exit.restore() - }) - - it('with runs, displays the results of the latest run', function * () { - const api = nock('https://api.heroku.com') - .get(`/pipelines/${pipeline.id}`) - .reply(200, pipeline) - .get(`/pipelines/${pipeline.id}/test-runs`) - .reply(200, [testRun]) - .get(`/pipelines/${pipeline.id}/test-runs/${testRun.number}`) - .reply(200, testRun) - .get(`/test-runs/${testRun.id}/test-nodes`) - .reply(200, [testNode]) - .get(`/test-runs/${testRun.id}/test-nodes`) - .reply(200, [testNode]) - - const streamAPI = nock('https://output.com') - .get('/setup') - .reply(200, setupOutput) - .get('/tests') - .reply(200, testOutput) - - yield cmd.run({ flags: { pipeline: pipeline.id } }) - expect(cli.stdout).to.contain(`✓ #${testRun.number}`) - - api.done() - streamAPI.done() - }) - - it('without any runs, reports that there are no runs', function * () { - let api = nock('https://api.heroku.com') - .get(`/pipelines/${pipeline.id}`) - .reply(200, pipeline) - .get(`/pipelines/${pipeline.id}/test-runs`) - .reply(200, []) - - yield cmd.run({ flags: { pipeline: pipeline.id } }) - expect(cli.stderr).to.contain('No Heroku CI runs found') - api.done() - }) -}) diff --git a/packages/ci/.circleci/config.yml b/packages/ci/.circleci/config.yml new file mode 100644 index 0000000000..ae56b9b74b --- /dev/null +++ b/packages/ci/.circleci/config.yml @@ -0,0 +1,65 @@ +--- +version: 2 +jobs: + node-latest: &test + docker: + - image: node:latest + working_directory: ~/cli + steps: + - checkout + - restore_cache: &restore_cache + keys: + - v1-npm-{{checksum ".circleci/config.yml"}}-{{ checksum "yarn.lock"}} + - v1-npm-{{checksum ".circleci/config.yml"}} + - run: + name: Install dependencies + command: .circleci/greenkeeper + - run: ./bin/run --help + - run: + name: Testing + command: yarn test + - run: + name: Submitting code coverage to codecov + command: | + ./node_modules/.bin/nyc report --reporter text-lcov > coverage.lcov + curl -s https://codecov.io/bash | bash + node-8: + <<: *test + docker: + - image: node:8 + release: + <<: *test + steps: + - add_ssh_keys + - checkout + - restore_cache: *restore_cache + - run: + name: Install dependencies + command: | + yarn global add @oclif/semantic-release@3 semantic-release@15 + yarn --frozen-lockfile + - run: + name: Cutting release + command: | + export PATH=/usr/local/share/.config/yarn/global/node_modules/.bin:$PATH + semantic-release -e @oclif/semantic-release + - save_cache: + key: v1-yarn-{{checksum ".circleci/config.yml"}}-{{checksum "yarn.lock"}} + paths: + - ~/cli/node_modules + - /usr/local/share/.cache/yarn + - /usr/local/share/.config/yarn + +workflows: + version: 2 + "@heroku-cli/plugin-ci": + jobs: + - node-latest + - node-8 + - release: + context: org-global + filters: + branches: {only: master} + requires: + - node-latest + - node-8 diff --git a/packages/ci/.circleci/greenkeeper b/packages/ci/.circleci/greenkeeper new file mode 100755 index 0000000000..bf73a3e4ed --- /dev/null +++ b/packages/ci/.circleci/greenkeeper @@ -0,0 +1,25 @@ +#!/usr/bin/env bash + +set -ex + +PATH=/usr/local/share/.config/yarn/global/node_modules/.bin:$PATH + +if [[ "$CIRCLE_BRANCH" != greenkeeper/* ]]; then + yarn + # yarn check + exit 0 +fi + +if [[ ! -z "$GIT_EMAIL" ]] & [[ ! -z "$GIT_USERNAME" ]]; then + git config --global push.default simple + git config --global user.email "$GIT_EMAIL" + git config --global user.name "$GIT_USERNAME" +fi + +if [[ ! -x "$(command -v greenkeeper-lockfile-update)" ]]; then + yarn global add greenkeeper-lockfile@1 +fi + +greenkeeper-lockfile-update +yarn +greenkeeper-lockfile-upload diff --git a/packages/ci/.editorconfig b/packages/ci/.editorconfig new file mode 100644 index 0000000000..beffa3084e --- /dev/null +++ b/packages/ci/.editorconfig @@ -0,0 +1,11 @@ +root = true + +[*] +indent_style = space +indent_size = 2 +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = true + +[*.md] +trim_trailing_whitespace = false diff --git a/packages/ci/.gitattributes b/packages/ci/.gitattributes new file mode 100644 index 0000000000..3beda43c37 --- /dev/null +++ b/packages/ci/.gitattributes @@ -0,0 +1,3 @@ +* text=auto +*.js text eol=lf +*.ts text eol=lf diff --git a/packages/ci/.gitignore b/packages/ci/.gitignore new file mode 100644 index 0000000000..9d6ea2ca58 --- /dev/null +++ b/packages/ci/.gitignore @@ -0,0 +1,8 @@ +*-debug.log +*-error.log +/.nyc_output +/dist +/lib +/package-lock.json +/tmp +node_modules diff --git a/packages/ci/.nycrc b/packages/ci/.nycrc new file mode 100644 index 0000000000..f4096bdffd --- /dev/null +++ b/packages/ci/.nycrc @@ -0,0 +1,12 @@ +{ + "extension": [ + ".ts" + ], + "include": [ + "src/**/*.ts" + ], + "exclude": [ + "**/*.d.ts" + ], + "all": true +} diff --git a/packages/ci/LICENSE b/packages/ci/LICENSE new file mode 100644 index 0000000000..753b079432 --- /dev/null +++ b/packages/ci/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2018 Raúl Barroso @raulb + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/packages/ci/README.md b/packages/ci/README.md new file mode 100644 index 0000000000..f3a830e0a0 --- /dev/null +++ b/packages/ci/README.md @@ -0,0 +1,60 @@ +@heroku-cli/plugin-ci +===================== + +Heroku CLI plugin for Heroku CI + +[![oclif](https://img.shields.io/badge/cli-oclif-brightgreen.svg)](https://oclif.io) +[![Version](https://img.shields.io/npm/v/@heroku-cli/plugin-ci.svg)](https://npmjs.org/package/@heroku-cli/plugin-ci) + +[![CircleCI](https://circleci.com/gh/heroku/cli/tree/master.svg?style=shield)](https://circleci.com/gh/heroku/cli/tree/master) + +[![Appveyor CI](https://ci.appveyor.com/api/projects/status/github/heroku/cli?branch=master&svg=true)](https://ci.appveyor.com/project/heroku/cli/branch/master) +[![Codecov](https://codecov.io/gh/heroku/cli/branch/master/graph/badge.svg)](https://codecov.io/gh/heroku/cli) +[![Downloads/week](https://img.shields.io/npm/dw/@heroku-cli/plugin-ci.svg)](https://npmjs.org/package/@heroku-cli/plugin-ci) +[![License](https://img.shields.io/npm/l/@heroku-cli/plugin-ci.svg)](https://github.com/heroku/cli/blob/master/package.json) + + +# Usage + +# Commands + +* [`heroku ci:info`](#heroku-ci-info) +* [`heroku ci:last`](#heroku-ci-last) +* [`heroku ci:run`](#heroku-ci-run) +* [`heroku ci:rerun`](#heroku-ci-rerun) + +## `heroku ci:info` + +Shows the information for a particular ci run on a pipeline. + +``` +USAGE + $ heroku ci:info 555 --pipeline=my-pipeline # 555 is the test number +``` + +## `heroku ci:last` + +Shows the information for the last run for a given pipeline. + +``` +USAGE + $ heroku ci:last --pipeline=my-pipeline +``` + +## `heroku ci:run` + +Run this from within your repo directory to trigger a test agains the current branch and commit. + +``` +USAGE + $ heroku ci:run --pipeline=my-pipeline +``` + +## `heroku ci:rerun` + +Re-run a previous test run. If no test run number is provided, the most recent test run will be re-run. + +``` +USAGE + $ heroku ci:rerun 555 --pipeline=my-pipeline # 555 is the test number +``` \ No newline at end of file diff --git a/packages/ci/appveyor.yml b/packages/ci/appveyor.yml new file mode 100644 index 0000000000..fb7fb5b27f --- /dev/null +++ b/packages/ci/appveyor.yml @@ -0,0 +1,21 @@ +environment: + nodejs_version: "9" +cache: + - '%LOCALAPPDATA%\Yarn -> appveyor.yml' + - node_modules -> yarn.lock + +install: + - ps: Install-Product node $env:nodejs_version x64 + - yarn +test_script: + - .\bin\run --help + - yarn test +after_test: + - .\node_modules\.bin\nyc report --reporter text-lcov > coverage.lcov + - ps: | + $env:PATH = 'C:\msys64\usr\bin;' + $env:PATH + Invoke-WebRequest -Uri 'https://codecov.io/bash' -OutFile codecov.sh + bash codecov.sh + +build: off + diff --git a/packages/ci/bin/run b/packages/ci/bin/run new file mode 100755 index 0000000000..3c4ae3ac07 --- /dev/null +++ b/packages/ci/bin/run @@ -0,0 +1,4 @@ +#!/usr/bin/env node + +require('@oclif/command').run() +.catch(require('@oclif/errors/handle')) diff --git a/packages/ci/bin/run.cmd b/packages/ci/bin/run.cmd new file mode 100644 index 0000000000..968fc30758 --- /dev/null +++ b/packages/ci/bin/run.cmd @@ -0,0 +1,3 @@ +@echo off + +node "%~dp0\run" %* diff --git a/packages/ci/package.json b/packages/ci/package.json new file mode 100644 index 0000000000..00afbf433d --- /dev/null +++ b/packages/ci/package.json @@ -0,0 +1,72 @@ +{ + "name": "@heroku-cli/plugin-ci", + "description": "Heroku CLI plugin for Heroku CI", + "version": "0.0.0", + "author": "Raúl Barroso @raulb", + "bugs": "https://github.com/heroku/cli/issues", + "dependencies": { + "@heroku-cli/color": "^1.1.9", + "@heroku-cli/command": "^8.1.26", + "@heroku-cli/schema": "^1.0.12", + "@oclif/command": "^1", + "@oclif/config": "^1", + "@types/inquirer": "0.0.42", + "@types/sinon": "^5.0.1", + "@types/validator": "^9.4.1", + "async-file": "^2.0.2", + "cli-ux": "^4.7.3", + "got": "^8.3.2", + "inquirer": "^6.0.0", + "tslib": "^1", + "validator": "^10.5.0" + }, + "devDependencies": { + "@fancy-test/nock": "^0.1.1", + "@oclif/dev-cli": "^1", + "@oclif/plugin-help": "^2", + "@oclif/test": "^1.1.0", + "@oclif/tslint": "^1", + "@types/chai": "^4", + "@types/mocha": "^5", + "@types/nock": "^9.3.0", + "@types/node": "^10", + "chai": "^4", + "globby": "^8", + "mocha": "^5", + "nock": "^9.2.5", + "nyc": "^12", + "ts-node": "^6", + "tslint": "^5", + "typescript": "^2.9" + }, + "engines": { + "node": ">=8.0.0" + }, + "files": [ + "/lib", + "/npm-shrinkwrap.json", + "/oclif.manifest.json", + "/yarn.lock" + ], + "homepage": "https://github.com/heroku/cli", + "keywords": [ + "oclif-plugin" + ], + "license": "MIT", + "oclif": { + "commands": "./lib/commands", + "bin": "heroku", + "devPlugins": [ + "@oclif/plugin-help" + ] + }, + "repository": "heroku/cli", + "scripts": { + "postpack": "rm -f oclif.manifest.json npm-shrinkwrap.json", + "posttest": "tsc -p test --noEmit && tslint -p test -t stylish", + "prepack": "rm -rf lib && tsc && oclif-dev manifest && oclif-dev readme && npm shrinkwrap", + "prepare": "rm -rf lib && tsc", + "test": "nyc mocha --forbid-only \"test/**/*.test.ts\"", + "version": "oclif-dev readme && git add README.md" + } +} diff --git a/packages/ci/src/commands/ci/info.ts b/packages/ci/src/commands/ci/info.ts new file mode 100644 index 0000000000..63ebdfded0 --- /dev/null +++ b/packages/ci/src/commands/ci/info.ts @@ -0,0 +1,32 @@ +import * as Heroku from '@heroku-cli/schema' + +import {Command, flags} from '@heroku-cli/command' + +import {getPipeline} from '../../utils/pipelines' +import {displayTestRunInfo} from '../../utils/test-run' + +export default class CiInfo extends Command { + static description = 'show the status of a specific test run' + + static examples = [ + `$ heroku ci:info 1288 --app murmuring-headland-14719 +`, + ] + + static flags = { + app: flags.app({required: false}), + node: flags.string({description: 'the node number to show its setup and output', required: false}), + pipeline: flags.pipeline({required: false}) + } + + static args = [{name: 'test-run', required: true}] + + async run() { + const {args, flags} = this.parse(CiInfo) + const pipeline = await getPipeline(flags, this) + const {body: testRun} = await this.heroku.get(`/pipelines/${pipeline.id}/test-runs/${args['test-run']}`) + const {body: testNodes} = await this.heroku.get(`/test-runs/${testRun.id}/test-nodes`) + + await displayTestRunInfo(this, testRun, testNodes, flags.node) + } +} diff --git a/packages/ci/src/commands/ci/last.ts b/packages/ci/src/commands/ci/last.ts new file mode 100644 index 0000000000..c786f5a59b --- /dev/null +++ b/packages/ci/src/commands/ci/last.ts @@ -0,0 +1,32 @@ +import * as Heroku from '@heroku-cli/schema' + +import {Command, flags} from '@heroku-cli/command' + +import {getPipeline} from '../../utils/pipelines' +import {displayTestRunInfo} from '../../utils/test-run' + +export default class CiLast extends Command { + static description = 'looks for the most recent run and returns the output of that run' + + static examples = [ + `$ heroku ci:last --app murmuring-headland-14719 --node 100 +`, + ] + + static flags = { + app: flags.app({required: false}), + node: flags.string({description: 'the node number to show its setup and output', required: false}), + pipeline: flags.pipeline({required: false}) + } + + async run() { + const {flags} = this.parse(CiLast) + const pipeline = await getPipeline(flags, this) + const headers = {Range: 'number ..; order=desc,max=1'} + const {body: latestTestRuns} = await this.heroku.get(`/pipelines/${pipeline.id}/test-runs`, {headers}) + const {body: testRun} = await this.heroku.get(`/pipelines/${pipeline.id}/test-runs/${latestTestRuns[0].number}`) + const {body: testNodes} = await this.heroku.get(`/test-runs/${testRun.id}/test-nodes`) + + await displayTestRunInfo(this, testRun, testNodes, flags.node) + } +} diff --git a/packages/ci/src/commands/ci/rerun.ts b/packages/ci/src/commands/ci/rerun.ts new file mode 100644 index 0000000000..442d476eff --- /dev/null +++ b/packages/ci/src/commands/ci/rerun.ts @@ -0,0 +1,66 @@ + +import {Command, flags} from '@heroku-cli/command' +import * as Heroku from '@heroku-cli/schema' + +import cli from 'cli-ux' + +import * as Kolkrabbi from '../../interfaces/kolkrabbi' + +import {getPipeline} from '../../utils/pipelines' +import {displayAndExit} from '../../utils/test-run' + +import {createSourceBlob} from '../../utils/source' + +export default class CiReRun extends Command { + static description = 'rerun tests against current directory' + + static examples = [ + `$ heroku ci:rerun 985 --app murmuring-headland-14719 +`, + ] + + static flags = { + app: flags.app({required: false}), + pipeline: flags.pipeline({required: false}) + } + + static args = [{name: 'number', required: false}] + + async run() { + const {flags, args} = this.parse(CiReRun) + const pipeline = await getPipeline(flags, this) + + let sourceTestRun: Heroku.TestRun + + if (args.number) { + const testRunResponse = await this.heroku.get(`/pipelines/${pipeline.id}/test-runs/${args.number}`) + sourceTestRun = testRunResponse.body + } else { + const {body: testRuns} = await this.heroku.get(`/pipelines/${pipeline.id}/test-runs`, {headers: {Range: 'number ..; order=desc,max=1'}}) + sourceTestRun = testRuns[0] + } + this.log(`Rerunning test run #${sourceTestRun.number}...`) + + cli.action.start('Preparing source') + const sourceBlobUrl = await createSourceBlob(sourceTestRun.commit_sha, this) + cli.done() + + const {body: pipelineRepository} = await this.heroku.get(`https://kolkrabbi.heroku.com/pipelines/${pipeline.id}/repository`) + + cli.action.start('Starting test run') + const organization = pipelineRepository.organization && pipelineRepository.organization.name + + const {body: testRun} = await this.heroku.post('/test-runs', {body: { + commit_branch: sourceTestRun.commit_branch, + commit_message: sourceTestRun.commit_message, + commit_sha: sourceTestRun.commit_sha, + pipeline: pipeline.id, + organization, + source_blob_url: sourceBlobUrl + } + }) + cli.done() + + await displayAndExit(pipeline, testRun.number!, this) + } +} diff --git a/packages/ci/src/commands/ci/run.ts b/packages/ci/src/commands/ci/run.ts new file mode 100644 index 0000000000..f1cbdbc651 --- /dev/null +++ b/packages/ci/src/commands/ci/run.ts @@ -0,0 +1,53 @@ + +import {Command, flags} from '@heroku-cli/command' +import * as Heroku from '@heroku-cli/schema' + +import cli from 'cli-ux' + +import * as Kolkrabbi from '../../interfaces/kolkrabbi' + +import {getPipeline} from '../../utils/pipelines' +import {displayAndExit} from '../../utils/test-run' + +import {createSourceBlob} from '../../utils/source' + +const git = require('../../utils/git') +export default class CiRun extends Command { + static description = 'run tests against current directory' + + static examples = [ + `$ heroku ci:run --app murmuring-headland-14719 +`, + ] + + static flags = { + app: flags.app({required: false}), + pipeline: flags.pipeline({required: false}) + } + + async run() { + const {flags} = this.parse(CiRun) + const pipeline = await getPipeline(flags, this) + const commit = await git.readCommit('HEAD') + + cli.action.start('Preparing source') + const sourceBlobUrl = await createSourceBlob(commit.ref, this) + cli.done() + + cli.action.start('Starting test run') + const {body: pipelineRepository} = await this.heroku.get(`https://kolkrabbi.heroku.com/pipelines/${pipeline.id}/repository`) + const organization = pipelineRepository.organization && pipelineRepository.organization.name + const {body: testRun} = await this.heroku.post('/test-runs', {body: { + commit_branch: commit.branch, + commit_message: commit.message, + commit_sha: commit.ref, + pipeline: pipeline.id, + organization, + source_blob_url: sourceBlobUrl + } + }) + cli.done() + + await displayAndExit(pipeline, testRun.number!, this) + } +} diff --git a/packages/ci/src/index.ts b/packages/ci/src/index.ts new file mode 100644 index 0000000000..b1c6ea436a --- /dev/null +++ b/packages/ci/src/index.ts @@ -0,0 +1 @@ +export default {} diff --git a/packages/ci/src/interfaces/kolkrabbi.ts b/packages/ci/src/interfaces/kolkrabbi.ts new file mode 100644 index 0000000000..97013ace07 --- /dev/null +++ b/packages/ci/src/interfaces/kolkrabbi.ts @@ -0,0 +1,312 @@ +/** + * This file was automatically generated by json-schema-to-typescript. + * DO NOT MODIFY IT BY HAND. Instead, modify the source JSONSchema file, + * and run json-schema-to-typescript to regenerate this file. + */ + +/** + * Kolkrabbi API. + */ +export interface KolkrabbiApi { + 'account-link'?: KolkrabbiApiAccountLink + 'app-json-schema'?: AppJsonSchema + 'app-json'?: KolkrabbiApiAppJson + apps?: KolkrabbiApiApps + organization?: HerokuPlatformApiOrganization + 'pipeline-repository'?: KolkrabbiApiPipelineRepositories + pipeline?: HerokuPlatformApiPipeline + 'pull-requests'?: KolkrabbiApiPullRequests + repository?: KolkrabbiApiRepositories + [k: string]: any +} +/** + * An account link represents the relationship between a Heroku user and a GitHub user. + */ +export interface KolkrabbiApiAccountLink { + /** + * unique identifier of an account link + */ + id?: string + /** + * Heroku details for the account link + */ + heroku?: { + /** + * unique identifier of the Heroku user + */ + user_id?: string + [k: string]: any + } + /** + * GitHub details for the account link + */ + github?: { + /** + * unique identifier of the GitHub user + */ + user_id?: number + [k: string]: any + } + [k: string]: any +} +export interface AppJsonSchema { + /** + * A clean and simple name to identify the template (30 characters max). + */ + name?: string + /** + * A brief summary of the app: what it does, who it's for, why it exists, etc. + */ + description?: string + /** + * An array of strings describing the app. + */ + keywords?: any[] + /** + * The project's website. + */ + website?: string + /** + * The location of the application's source code, such as a Git URL, GitHub URL, Subversion URL, or Mercurial URL. + */ + repository?: string + /** + * The URL of the application's logo image. Dimensions should be square. Format can be SVG, PNG, or JPG. + */ + logo?: string + /** + * A URL specifying where to redirect the user once their new app is deployed. If value is a fully-qualified URL, the user should be redirected to that URL. If value begins with a slash `/`, the user should be redirected to that path in their newly deployed app. + */ + success_url?: string + /** + * A key-value object specifying scripts or shell commands to execute at different stages in the build/release process. Currently, `postdeploy` is the only supported script. + */ + scripts?: { + [k: string]: any + } + /** + * A key-value object for environment variables, or [config vars](https://devcenter.heroku.com/articles/config-vars) in Heroku parlance. Keys are the names of the environment variables. Values can be strings or objects. If the value is a string, it will be used. If the value is an object, it defines specific requirements for that variable: + * + * - `description`: a human-friendly blurb about what the value is for and how to determine what it should be + * - `value`: a default value to use. This should always be a string. + * - `required`: A boolean indicating whether the given value is required for the app to function (default: `true`). + * - `generator`: a string representing a function to call to generate the value. Currently the only supported generator is `secret`, which generates a pseudo-random string of characters. + */ + env?: { + [k: string]: any + } + /** + * An array of strings specifying Heroku addons to provision on the app before deploying. Each addon should be in the format `addon:plan` or `addon`. If plan is omitted, that addon's default plan will be provisioned. + */ + addons?: any[] + /** + * An ordered array of objects specifying the buildpacks to be applied to this app + */ + buildpacks?: any[] + /** + * Dynos to scale on the app before deploying. + */ + formation?: { + [k: string]: any + } +} +export interface KolkrabbiApiAppJson { + app_json?: AppJsonSchema + /** + * name of branch to commit to + */ + branch?: string | null + [k: string]: any +} +/** + * FIXME + */ +export interface KolkrabbiApiApps { + /** + * unique identifier of app + */ + app_id?: string + /** + * when app was created + */ + created_at?: string + /** + * unique identifier of app + */ + id?: string + /** + * when app was updated + */ + updated_at?: string | null + [k: string]: any +} +/** + * Deprecated: Organizations allow you to manage access to a shared group of applications across your development team. + */ +export interface HerokuPlatformApiOrganization { + /** + * unique identifier of organization + */ + id?: string + /** + * when the organization was created + */ + created_at?: string + /** + * whether charges incurred by the org are paid by credit card. + */ + credit_card_collections?: boolean + /** + * whether to use this organization when none is specified + */ + default?: boolean + /** + * upper limit of members allowed in an organization. + */ + membership_limit?: number | null + /** + * unique name of organization + */ + name?: string + /** + * whether the org is provisioned licenses by salesforce. + */ + provisioned_licenses?: boolean + /** + * role in the organization + */ + role?: 'admin' | 'collaborator' | 'member' | 'owner' | null + /** + * type of organization. + */ + type?: 'enterprise' | 'team' + /** + * when the organization was updated + */ + updated_at?: string + [k: string]: any +} +/** + * Pipeline repositories link a pipeline to a Github repository. + */ +export interface KolkrabbiApiPipelineRepositories { + /** + * whether automatic review apps is enabled + */ + automatic_review_apps?: boolean + /** + * whether CI is enabled + */ + ci?: boolean + /** + * unique identifier of a pipeline repository + */ + id?: string + creator?: KolkrabbiApiAccountLink + /** + * when the pipeline repository was created + */ + created_at?: string + /** + * organization tied to this pipeline repository + */ + organization?: { + [k: string]: any + } | null + owner?: KolkrabbiApiAccountLink + pipeline?: HerokuPlatformApiPipeline + repository?: KolkrabbiApiRepositories + /** + * whether review apps is enabled + */ + review_apps?: boolean + /** + * a collection of statuses + */ + statuses?: any[] + /** + * when pipeline repository was updated + */ + updated_at?: string | null + [k: string]: any +} +/** + * A pipeline allows grouping of apps into different stages. + */ +export interface HerokuPlatformApiPipeline { + /** + * unique identifier of pipeline + */ + id?: string + [k: string]: any +} +/** + * A Repository is a reference to a remote DVCs codebase + */ +export interface KolkrabbiApiRepositories { + /** + * The id that the remote DVCS uses for the repository + */ + id?: number + /** + * The name for the remote DVCS uses for the repository + */ + name?: string + /** + * The type of DVCS + */ + type?: string + /** + * when the repository reference was created + */ + created_at?: string + /** + * when repository was updated + */ + updated_at?: string | null + [k: string]: any +} +/** + * FIXME + */ +export interface KolkrabbiApiPullRequests { + app_setup?: { + /** + * unique identifier of app setup + */ + id?: string + /** + * the overall status of app setup + */ + status?: 'failed' | 'pending' | 'succeeded' + [k: string]: any + } + /** + * when app was created + */ + created_at?: string + pull_request?: { + /** + * unique identifier of pull request + */ + id?: number + /** + * pull request number + */ + number?: number + /** + * unique name of app + */ + ref?: string + /** + * pull request title + */ + title?: string + [k: string]: any + } + /** + * when app was updated + */ + updated_at?: string | null + [k: string]: any +} diff --git a/packages/ci/src/utils/git.js b/packages/ci/src/utils/git.js new file mode 100644 index 0000000000..d00d148036 --- /dev/null +++ b/packages/ci/src/utils/git.js @@ -0,0 +1,88 @@ +const spawn = require('child_process').spawn +const Promise = require('bluebird') +const fs = Promise.promisifyAll(require('fs')) +const tmp = Promise.promisifyAll(require('temp').track()) +const gh = require('github-url-to-object') + +const NOT_A_GIT_REPOSITORY = 'not a git repository' +const RUN_IN_A_GIT_REPOSITORY = 'Please run this command from the directory containing your project\'s git repo' + +const NOT_ON_A_BRANCH = new Error('not a symbolic ref') +const CHECKOUT_A_BRANCH = new Error('Please checkout a branch before running this command') + +function runGit (...args) { + const git = spawn('git', args) + + return new Promise((resolve, reject) => { + git.on('exit', (exitCode) => { + if (exitCode === 0) { + return + } + + const error = (git.stderr.read() || 'unknown error').toString().trim() + if (error.toLowerCase().includes(NOT_A_GIT_REPOSITORY)) { + reject(RUN_IN_A_GIT_REPOSITORY) + return + } + if (error.includes(NOT_ON_A_BRANCH)) { + reject(CHECKOUT_A_BRANCH) + return + } + reject(new Error(`Error while running 'git ${args.join(' ')}' (${error})`)) + }) + + git.stdout.on('data', (data) => resolve(data.toString().trim())) + }) +} + +async function getRef (branch) { + return runGit('rev-parse', branch || 'HEAD') +} + +async function getBranch (symbolicRef) { + return runGit('symbolic-ref', '--short', symbolicRef) +} + +async function getCommitTitle (ref) { + return runGit('log', ref || '', '-1', '--pretty=format:%s') +} + +async function createArchive (ref) { + const tar = spawn('git', ['archive', '--format', 'tar.gz', ref]) + const file = await tmp.openAsync({ suffix: '.tar.gz' }) + const write = tar.stdout.pipe(fs.createWriteStream(file.path)) + + return new Promise((resolve, reject) => { + write.on('close', () => resolve(file.path)) + write.on('error', reject) + }) +} + +async function githubRepository () { + const remote = await runGit('remote', 'get-url', 'origin') + const repository = gh(remote) + + if (repository === null) { + throw new Error('Not a GitHub repository') + } + + return repository +} + +async function readCommit (commit) { + const branch = await getBranch('HEAD') + const ref = await getRef(commit) + const message = await getCommitTitle(ref) + + return Promise.resolve({ + branch: branch, + ref: ref, + message: message + }) +} + +module.exports = { + createArchive, + githubRepository, + readCommit +} diff --git a/packages/ci/src/utils/pipelines.ts b/packages/ci/src/utils/pipelines.ts new file mode 100644 index 0000000000..a2f8466634 --- /dev/null +++ b/packages/ci/src/utils/pipelines.ts @@ -0,0 +1,57 @@ +import {prompt} from 'inquirer' +import {isUUID} from 'validator' + +import {Command} from '@heroku-cli/command' + +import * as Heroku from '@heroku-cli/schema' + +export async function getPipeline(flags: any, command: Command) { + let pipeline + + if ((!flags.pipeline) && (!flags.app)) { + command.error('Required flag: --pipeline PIPELINE or --app APP') + } + + if (flags && flags.pipeline) { + pipeline = await disambiguatePipeline(flags.pipeline, command) + + if (pipeline.pipeline) { pipeline = pipeline.pipeline } // in case prompt returns an object like { pipeline: { ... } } + } else { + const {body: coupling} = await command.heroku.get(`/apps/${flags.app}/pipeline-couplings`) + if ((coupling) && (coupling.pipeline)) { + pipeline = coupling.pipeline + } else { + command.error(`No pipeline found with application ${flags.app}`) + } + } + + return pipeline +} +export async function disambiguatePipeline(pipelineIDOrName: any, command: Command) { + const headers = {Accept: 'application/vnd.heroku+json; version=3.pipelines'} + + if (isUUID(pipelineIDOrName)) { + const {body: pipeline} = await command.heroku.get(`/pipelines/${pipelineIDOrName}`, {headers}) + return pipeline + } else { + const {body: pipelines} = await command.heroku.get(`/pipelines?eq[name]=${pipelineIDOrName}`, {headers}) + + switch (pipelines.length) { + case 0: + command.error('Pipeline not found') + break + case 1: + return pipelines[0] + default: + let choices = pipelines.map(function (x: Heroku.Pipeline) { return {name: new Date(x.created_at!), value: x} }) + let questions = [{ + type: 'list', + name: 'pipeline', + message: `Which ${pipelineIDOrName} pipeline?`, + choices + }] + + return prompt(questions) + } + } +} diff --git a/packages/ci/src/utils/source.ts b/packages/ci/src/utils/source.ts new file mode 100644 index 0000000000..31e8d877a8 --- /dev/null +++ b/packages/ci/src/utils/source.ts @@ -0,0 +1,49 @@ +'use strict' +const got = require('got') +const git = require('./git') +import {Command} from '@heroku-cli/command' + +import * as fs from 'async-file' + +async function uploadArchive(url: string, filePath: string) { + const request = got.stream.put(url, { + headers: { + 'content-length': (await fs.stat(filePath)).size + } + }) + + fs.createReadStream(filePath).pipe(request) + + return new Promise((resolve: any, reject: any) => { + request.on('error', reject) + request.on('response', resolve) + }) +} + +async function prepareSource(ref: any, command: Command) { + const [filePath, source] = await [ + git.createArchive(ref), + command.heroku.post('/sources', {body: command}) + ] + await uploadArchive(source.source_blob.put_url, filePath) + return Promise.resolve(source) +} + +async function urlExists(url: any) { + return got.head(url) +} + +export async function createSourceBlob(ref: any, command: Command) { + try { + const githubRepository = await git.githubRepository() + const {user, repo} = githubRepository + + let {body: archiveLink} = await command.heroku.get(`https://kolkrabbi.heroku.com/github/repos/${user}/${repo}/tarball/${ref}`) + if (await urlExists(archiveLink.archive_link)) { + return archiveLink.archive_link + } + } catch (ex) { command.error(ex) } + + const sourceBlob = await prepareSource(ref, command) + return sourceBlob.source_blob.get_url +} diff --git a/packages/ci/src/utils/test-run.ts b/packages/ci/src/utils/test-run.ts new file mode 100644 index 0000000000..a000ecff89 --- /dev/null +++ b/packages/ci/src/utils/test-run.ts @@ -0,0 +1,164 @@ +import color from '@heroku-cli/color' +import {get, RequestOptions} from 'https' + +import cli from 'cli-ux' + +import {Command} from '@heroku-cli/command' + +import * as Heroku from '@heroku-cli/schema' +import * as http from 'http' + +function logStream(url: RequestOptions | string, fn: (res: http.IncomingMessage) => void) { + return get(url, fn) +} + +function stream(url: string) { + return new Promise((resolve, reject) => { + const request = logStream(url, output => { + output.on('data', data => { + if (data.toString() === Buffer.from('').toString()) { + request.abort() + resolve() + } + }) + + output.on('end', () => resolve()) + output.on('error', e => reject(e)) + output.pipe(process.stdout) + }) + }) +} + +function statusIcon({status}: Heroku.TestRun | Heroku.TestNode) { + if (!status) { return color.yellow('-') } + + switch (status) { + case 'pending': + case 'creating': + case 'building': + case 'running': + case 'debugging': + return color.yellow('-') + case 'errored': + return color.red('!') + case 'failed': + return color.red('✗') + case 'succeeded': + return color.green('✓') + case 'cancelled': + return color.yellow('!') + default: + return color.yellow('?') + + } +} + +function printLine(testRun: Heroku.TestRun) { + return `${statusIcon(testRun)} #${testRun.number} ${testRun.commit_branch}:${testRun.commit_sha!.slice(0, 7)} ${testRun.status}` +} + +function printLineTestNode(testNode: Heroku.TestNode) { + return `${statusIcon(testNode)} #${testNode.index} ${testNode.status}` +} + +function processExitCode(command: Command, testNode: Heroku.TestNode) { + if (testNode.exit_code && testNode.exit_code !== 0) { + command.exit(testNode.exit_code) + } +} + +async function renderNodeOutput(command: Command, testRun: Heroku.TestRun, testNode: Heroku.TestNode) { + await stream(testNode.setup_stream_url!) + await stream(testNode.output_stream_url!) + + command.log() + command.log(printLine(testRun)) +} + +const BUILDING = 'building' +const RUNNING = 'running' +const ERRORED = 'errored' +const FAILED = 'failed' +const SUCCEEDED = 'succeeded' +const CANCELLED = 'cancelled' + +const TERMINAL_STATES = [SUCCEEDED, FAILED, ERRORED, CANCELLED] +const RUNNING_STATES = [RUNNING].concat(TERMINAL_STATES) +const BUILDING_STATES = [BUILDING, RUNNING].concat(TERMINAL_STATES) + +async function waitForStates(states: string[], testRun: Heroku.TestRun, command: Command) { + let newTestRun = testRun + + while (!states.includes(newTestRun.status!.toString())) { + let {body: bodyTestRun} = await command.heroku.get(`/pipelines/${testRun.pipeline!.id}/test-runs/${testRun.number}`) + newTestRun = bodyTestRun + } + return newTestRun +} + +async function display(pipeline: Heroku.Pipeline, number: number, command: Command) { + let {body: testRun} = await command.heroku.get(`/pipelines/${pipeline.id}/test-runs/${number}`) + if (testRun) { + cli.action.start('Waiting for build to start') + testRun = await waitForStates(BUILDING_STATES, testRun, command) + cli.done() + + let {body: testNodes} = await command.heroku.get(`/test-runs/${testRun.id}/test-nodes`) + let firstTestNode = testNodes[0] + + if (firstTestNode) { await stream(firstTestNode.setup_stream_url!) } + + if (testRun) { testRun = await waitForStates(RUNNING_STATES, testRun, command) } + if (firstTestNode) { await stream(firstTestNode.output_stream_url!) } + + if (testRun) { testRun = await waitForStates(TERMINAL_STATES, testRun, command) } + + // At this point, we know that testRun has a finished status, + // and we can check for exit_code from firstTestNode + if (testRun) { + let {body: newTestNodes} = await command.heroku.get(`/test-runs/${testRun.id}/test-nodes`) + firstTestNode = newTestNodes[0] + + command.log() + command.log(printLine(testRun)) + } + return firstTestNode + } +} + +export async function displayAndExit(pipeline: Heroku.Pipeline, number: number, command: Command) { + let testNode = await display(pipeline, number, command) + + testNode ? processExitCode(command, testNode) : command.exit(1) +} + +export async function displayTestRunInfo(command: Command, testRun: Heroku.TestRun, testNodes: Heroku.TestNode[], nodeArg: string | undefined) { + let testNode: Heroku.TestNode + + if (nodeArg) { + const nodeIndex = parseInt(nodeArg, 2) + testNode = testNodes.length > 1 ? testNodes[nodeIndex] : testNodes[0] + + await renderNodeOutput(command, testRun, testNode) + + if (testNodes.length === 1) { + command.log() + command.warn('This pipeline doesn\'t have parallel test runs, but you specified a node') + command.warn('See https://devcenter.heroku.com/articles/heroku-ci-parallel-test-runs for more info') + } + processExitCode(command, testNode) + } else { + if (testNodes.length > 1) { + command.log(printLine(testRun)) + command.log() + + testNodes.forEach(testNode => { + command.log(printLineTestNode(testNode)) + }) + } else { + testNode = testNodes[0] + await renderNodeOutput(command, testRun, testNode) + processExitCode(command, testNode) + } + } +} diff --git a/packages/ci/test/commands/ci/info.test.ts b/packages/ci/test/commands/ci/info.test.ts new file mode 100644 index 0000000000..93b753dd9f --- /dev/null +++ b/packages/ci/test/commands/ci/info.test.ts @@ -0,0 +1,310 @@ +import Nock from '@fancy-test/nock' +import * as Test from '@oclif/test' + +const test = Test.test +.register('nock', Nock) +const expect = Test.expect + +describe('ci:info', () => { + const testRunNumber = 10 + const testRun = {id: 'f53d34b4-c3a9-4608-a186-17257cf71d62', number: 10} + + test + .command(['ci:info']) + .catch(e => { + expect(e.message).to.contain('Missing 1 required arg:\ntest-run\nSee more help with --help') + }) + .it('errors when not specifying a test run') + + test + .command(['ci:info', `${testRun.number}`]) + .catch(e => { + expect(e.message).to.contain('Required flag: --pipeline PIPELINE or --app APP') + }) + .it('errors when not specifying a pipeline or an app') + + describe('when specifying a pipeline', () => { + const pipeline = {id: '14402644-c207-43aa-9bc1-974a34914010', name: 'pipeline'} + + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${testRunNumber}`) + .reply(200, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + ) + + api.get(`/test-runs/${testRun.id}/test-nodes`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + status: 'succeeded', + setup_stream_url: `https://test-setup-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}` + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test output') + }) + .command(['ci:info', `${testRun.number}`, `--pipeline=${pipeline.name}`]) + .it('it shows the setup, test, and final result output', ({stdout}) => { + expect(stdout).to.equal('Test setup outputTest output\n✓ #10 master:b9e982a succeeded\n') + }) + + describe('and the exit was not successful', () => { + const testRunExitCode = 34 + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${testRunNumber}`) + .reply(200, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + status: 'failed' + } + ) + + api.get(`/test-runs/${testRun.id}/test-nodes`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: testRunExitCode, + status: 'succeeded', + setup_stream_url: `https://test-setup-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}` + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test output') + }) + .command(['ci:info', `${testRun.number}`, `--pipeline=${pipeline.name}`]) + .exit(testRunExitCode) + .it('it shows the setup, test, and final result output', ({stdout}) => { + expect(stdout).to.equal('Test setup outputTest output\n✗ #10 master:b9e982a failed\n') + }) + }) + + describe('when the pipeline has parallel test runs enabled', () => { + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${testRunNumber}`) + .reply(200, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + ) + + api.get(`/test-runs/${testRun.id}/test-nodes`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + index: 0, + status: 'succeeded' + }, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + index: 1, + status: 'succeeded' + } + ]) + }) + .command(['ci:info', `${testRun.number}`, `--pipeline=${pipeline.name}`]) + .it('shows a result for each node', ({stdout}) => { + expect(stdout).to.equal('✓ #10 master:b9e982a succeeded\n\n✓ #0 succeeded\n✓ #1 succeeded\n') + }) + + describe('and the user passes in a test node index', () => { + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${testRunNumber}`) + .reply(200, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + ) + + api.get(`/test-runs/${testRun.id}/test-nodes`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + index: 0, + status: 'succeeded' + }, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + index: 1, + setup_stream_url: `https://test-setup-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`, + status: 'succeeded' + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test output') + }) + .command(['ci:info', `${testRun.number}`, `--pipeline=${pipeline.name}`, '--node=1']) + .it('displays the setup and test output for the specified node', ({stdout}) => { + expect(stdout).to.equal('Test setup outputTest output\n✓ #10 master:b9e982a succeeded\n') + }) + + describe('and the pipeline does not have parallel tests enabled', () => { + test + .stdout() + .stderr() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${testRunNumber}`) + .reply(200, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + ) + + api.get(`/test-runs/${testRun.id}/test-nodes`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRun.id, + number: testRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + index: 1, + setup_stream_url: `https://test-setup-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`, + status: 'succeeded' + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRun.id.substring(0, 3)}/test-runs/${testRun.id}`) + .reply(200, 'Test output') + }) + .command(['ci:info', `${testRun.number}`, `--pipeline=${pipeline.name}`, '--node=1']) + .it('displays the setup and test output for the first node and a warning', ({stdout, stderr}) => { + expect(stdout).to.equal('Test setup outputTest output\n✓ #10 master:b9e982a succeeded\n\n') + expect(stderr).to.contain('Warning: This pipeline doesn\'t have parallel test runs') + }) + }) + }) + }) + }) + + describe('when specifying an application', () => { + // TODO: Check it has a similar behaviour, but via pipeline couplings + }) +}) diff --git a/packages/ci/test/commands/ci/last.test.ts b/packages/ci/test/commands/ci/last.test.ts new file mode 100644 index 0000000000..702ba99a6c --- /dev/null +++ b/packages/ci/test/commands/ci/last.test.ts @@ -0,0 +1,93 @@ +import Nock from '@fancy-test/nock' +import * as Test from '@oclif/test' + +const test = Test.test +.register('nock', Nock) +const expect = Test.expect + +describe('ci:last', () => { + const testRunNumber = 10 + const testRunId = 'f53d34b4-c3a9-4608-a186-17257cf71d62' + + test + .command(['ci:last']) + .catch(e => { + expect(e.message).to.contain('Required flag: --pipeline PIPELINE or --app APP') + }) + .it('errors when not specifying a pipeline or an app') + + describe('when specifying a pipeline', () => { + const pipeline = {id: '14402644-c207-43aa-9bc1-974a34914010', name: 'pipeline'} + + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${testRunNumber}`) + .reply(200, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRunId, + number: testRunNumber, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + ) + + api.get(`/pipelines/${pipeline.id}/test-runs`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5849 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRunId, + number: testRunNumber, + pipeline: {id: pipeline.id}, + status: 'succeeded' + }, + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: 'testRun.id', + number: 9, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + ]) + + api.get(`/test-runs/${testRunId}/test-nodes`) + .reply(200, [ + { + commit_branch: 'master', + commit_message: 'Merge pull request #5848 from heroku/cli', + commit_sha: 'b9e982a60904730510a1c9e2dd2df64aef6f0d84', + id: testRunId, + number: testRunNumber, + pipeline: {id: pipeline.id}, + status: 'succeeded', + setup_stream_url: `https://test-setup-output.heroku.com/streams/${testRunId.substring(0, 3)}/test-runs/${testRunId}`, + output_stream_url: `https://test-output.heroku.com/streams/${testRunId.substring(0, 3)}/test-runs/${testRunId}`, + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRunId.substring(0, 3)}/test-runs/${testRunId}`) + .reply(200, 'Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${testRunId.substring(0, 3)}/test-runs/${testRunId}`) + .reply(200, 'Test output') + }) + .command(['ci:last', `--pipeline=${pipeline.name}`]) + .it('and a pipeline without parallel test runs it shows node output', ({stdout}) => { + expect(stdout).to.equal('Test setup outputTest output\n✓ #10 master:b9e982a succeeded\n') + }) + }) +}) diff --git a/packages/ci/test/commands/ci/rerun.test.ts b/packages/ci/test/commands/ci/rerun.test.ts new file mode 100644 index 0000000000..1958d3db4a --- /dev/null +++ b/packages/ci/test/commands/ci/rerun.test.ts @@ -0,0 +1,209 @@ +import Nock from '@fancy-test/nock' +import * as Test from '@oclif/test' +const git = require('../../../src/utils/git') + +const test = Test.test +.register('nock', Nock) +const expect = Test.expect + +describe('ci:rerun', () => { + test + .command(['ci:rerun']) + .catch(e => { + expect(e.message).to.contain('Required flag: --pipeline PIPELINE or --app APP') + }) + .it('errors when not specifying a pipeline or an app') + + describe('when specifying a pipeline', () => { + const pipeline = {id: '14402644-c207-43aa-9bc1-974a34914010', name: 'pipeline'} + const ghRepository = { + user: 'heroku-fake', repo: 'my-repo', ref: '668a5ce22eefc7b67c84c1cfe3a766f1958e0add', branch: 'my-test-branch' + } + const oldTestRun = { + commit_branch: ghRepository.branch, + commit_message: 'earlier commit', + commit_sha: '2F3CAFFD6AEEC967A7D71EB7ABEC0993D036430691E668A8710248DF4541111E', + id: 'd76b690b-a4ce-4a7b-83ca-c30792d4f3be', + number: 10, + pipeline: {id: pipeline.id}, + status: 'failed' + } + const newTestRun = { + commit_branch: ghRepository.branch, + commit_message: 'lastest commit', + commit_sha: ghRepository.ref, + id: 'b6512323-3a11-43ac-b4e4-9668b6a6b30c', + number: 11, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + const gitFake = { + readCommit: () => ({branch: ghRepository.branch, ref: ghRepository.ref}), + remoteFromGitConfig: () => Promise.resolve('heroku'), + getBranch: () => Promise.resolve(ghRepository.branch), + getRef: () => Promise.resolve(ghRepository.ref), + getCommitTitle: () => Promise.resolve(`pushed to ${ghRepository.branch}`), + githubRepository: () => Promise.resolve({user: ghRepository.user, repo: ghRepository.repo}), + createArchive: () => Promise.resolve('https://someurl'), + spawn: () => Promise.resolve(), + urlExists: () => Promise.resolve(), + exec: (args: any) => { + switch (args.join(' ')) { + case 'remote': + return Promise.resolve('heroku') + default: + return Promise.resolve() + } + } + } + + describe('when not specifying a run #', () => { + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs`) + .reply(200, [oldTestRun]) + + api.post('/test-runs') + .reply(200, newTestRun) + + api.get(`/pipelines/${pipeline.id}/test-runs/${newTestRun.number}`) + .reply(200, newTestRun) + + api.get(`/test-runs/${newTestRun.id}/test-nodes`) + .times(2) + .reply(200, [ + { + commit_branch: newTestRun.commit_branch, + commit_message: newTestRun.commit_message, + commit_sha: newTestRun.commit_sha, + id: newTestRun.id, + number: newTestRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + status: newTestRun.status, + setup_stream_url: `https://test-setup-output.heroku.com/streams/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}` + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`) + .reply(200, 'New Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`) + .reply(200, 'New Test output') + }) + .nock('https://kolkrabbi.heroku.com', kolkrabbiAPI => { + kolkrabbiAPI.get(`/github/repos/${ghRepository.user}/${ghRepository.repo}/tarball/${oldTestRun.commit_sha}`). + reply(200, { + archive_link: 'https://kolkrabbi.heroku.com/source/archive/gAAAAABb' + }) + kolkrabbiAPI.get(`/pipelines/${pipeline.id}/repository`) + .reply(200, { + ci: true, + organization: {id: 'e037ed63-5781-48ee-b2b7-8c55c571b63e'}, + owner: { + id: '463147bf-d572-41cf-bbf4-11ebc1c0bc3b', + heroku: { + user_id: '463147bf-d572-41cf-bbf4-11ebc1c0bc3b' }, + github: {user_id: 306015} + }, + repository: { + id: 138865824, + name: 'raulb/atleti', + type: 'github' + } + }) + kolkrabbiAPI.head('/source/archive/gAAAAABb') + .reply(200) + }) + .stub(git, 'githubRepository', gitFake.githubRepository) + .command(['ci:rerun', `--pipeline=${pipeline.name}`]) + .it('it runs the test and displays the test output for the first node', ({stdout}) => { + expect(stdout).to.equal('Rerunning test run #10...\nNew Test setup outputNew Test output\n✓ #11 my-test-branch:668a5ce succeeded\n') + }) + }) + + describe('when specifying a run #', () => { + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.get(`/pipelines/${pipeline.id}/test-runs/${oldTestRun.number}`) + .reply(200, oldTestRun) + + api.post('/test-runs') + .reply(200, newTestRun) + + api.get(`/pipelines/${pipeline.id}/test-runs/${newTestRun.number}`) + .reply(200, newTestRun) + + api.get(`/test-runs/${newTestRun.id}/test-nodes`) + .times(2) + .reply(200, [ + { + commit_branch: newTestRun.commit_branch, + commit_message: newTestRun.commit_message, + commit_sha: newTestRun.commit_sha, + id: newTestRun.id, + number: newTestRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + status: newTestRun.status, + setup_stream_url: `https://test-setup-output.heroku.com/streams/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}` + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`) + .reply(200, 'New Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`) + .reply(200, 'New Test output') + }) + .nock('https://kolkrabbi.heroku.com', kolkrabbiAPI => { + kolkrabbiAPI.get(`/github/repos/${ghRepository.user}/${ghRepository.repo}/tarball/${oldTestRun.commit_sha}`). + reply(200, { + archive_link: 'https://kolkrabbi.heroku.com/source/archive/gAAAAABb' + }) + kolkrabbiAPI.get(`/pipelines/${pipeline.id}/repository`) + .reply(200, { + ci: true, + organization: {id: 'e037ed63-5781-48ee-b2b7-8c55c571b63e'}, + owner: { + id: '463147bf-d572-41cf-bbf4-11ebc1c0bc3b', + heroku: { + user_id: '463147bf-d572-41cf-bbf4-11ebc1c0bc3b' }, + github: {user_id: 306015} + }, + repository: { + id: 138865824, + name: 'raulb/atleti', + type: 'github' + } + }) + kolkrabbiAPI.head('/source/archive/gAAAAABb') + .reply(200) + }) + .stub(git, 'githubRepository', gitFake.githubRepository) + .command(['ci:rerun', `${oldTestRun.number}` , `--pipeline=${pipeline.name}`]) + .it('it runs the test and displays the test output for the first node', ({stdout}) => { + expect(stdout).to.equal('Rerunning test run #10...\nNew Test setup outputNew Test output\n✓ #11 my-test-branch:668a5ce succeeded\n') + }) + }) + + }) +}) diff --git a/packages/ci/test/commands/ci/run.test.ts b/packages/ci/test/commands/ci/run.test.ts new file mode 100644 index 0000000000..ed84254a21 --- /dev/null +++ b/packages/ci/test/commands/ci/run.test.ts @@ -0,0 +1,123 @@ +import Nock from '@fancy-test/nock' +import * as Test from '@oclif/test' +const git = require('../../../src/utils/git') + +const test = Test.test +.register('nock', Nock) +const expect = Test.expect + +describe('ci:run', () => { + test + .command(['ci:run']) + .catch(e => { + expect(e.message).to.contain('Required flag: --pipeline PIPELINE or --app APP') + }) + .it('errors when not specifying a pipeline or an app') + + describe('when specifying a pipeline', () => { + const pipeline = {id: '14402644-c207-43aa-9bc1-974a34914010', name: 'pipeline'} + const ghRepository = { + user: 'heroku-fake', repo: 'my-repo', ref: '668a5ce22eefc7b67c84c1cfe3a766f1958e0add', branch: 'my-test-branch' + } + const newTestRun = { + commit_branch: ghRepository.branch, + commit_message: 'lastest commit', + commit_sha: ghRepository.ref, + id: 'b6512323-3a11-43ac-b4e4-9668b6a6b30c', + number: 11, + pipeline: {id: pipeline.id}, + status: 'succeeded' + } + + const gitFake = { + readCommit: () => ({branch: ghRepository.branch, ref: ghRepository.ref}), + remoteFromGitConfig: () => Promise.resolve('heroku'), + getBranch: () => Promise.resolve(ghRepository.branch), + getRef: () => Promise.resolve(ghRepository.ref), + getCommitTitle: () => Promise.resolve(`pushed to ${ghRepository.branch}`), + githubRepository: () => Promise.resolve({user: ghRepository.user, repo: ghRepository.repo}), + createArchive: () => Promise.resolve('https://someurl'), + spawn: () => Promise.resolve(), + urlExists: () => Promise.resolve(), + exec: (args: any) => { + switch (args.join(' ')) { + case 'remote': + return Promise.resolve('heroku') + default: + return Promise.resolve() + } + } + } + + test + .stdout() + .nock('https://api.heroku.com', api => { + api.get(`/pipelines?eq[name]=${pipeline.name}`) + .reply(200, [ + {id: pipeline.id} + ]) + + api.post('/test-runs') + .reply(200, newTestRun) + + api.get(`/pipelines/${pipeline.id}/test-runs/${newTestRun.number}`) + .reply(200, newTestRun) + + api.get(`/test-runs/${newTestRun.id}/test-nodes`) + .times(2) + .reply(200, [ + { + commit_branch: newTestRun.commit_branch, + commit_message: newTestRun.commit_message, + commit_sha: newTestRun.commit_sha, + id: newTestRun.id, + number: newTestRun.number, + pipeline: {id: pipeline.id}, + exit_code: 0, + status: newTestRun.status, + setup_stream_url: `https://test-setup-output.heroku.com/streams/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`, + output_stream_url: `https://test-output.heroku.com/streams/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}` + } + ]) + }) + .nock('https://test-setup-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`) + .reply(200, 'New Test setup output') + }) + .nock('https://test-output.heroku.com/streams', testOutputAPI => { + testOutputAPI.get(`/${newTestRun.id.substring(0, 3)}/test-runs/${newTestRun.id}`) + .reply(200, 'New Test output') + }) + .nock('https://kolkrabbi.heroku.com', kolkrabbiAPI => { + kolkrabbiAPI.get(`/github/repos/${ghRepository.user}/${ghRepository.repo}/tarball/${ghRepository.ref}`). + reply(200, { + archive_link: 'https://kolkrabbi.heroku.com/source/archive/gAAAAABb' + }) + kolkrabbiAPI.get(`/pipelines/${pipeline.id}/repository`) + .reply(200, { + ci: true, + organization: {id: 'e037ed63-5781-48ee-b2b7-8c55c571b63e'}, + owner: { + id: '463147bf-d572-41cf-bbf4-11ebc1c0bc3b', + heroku: { + user_id: '463147bf-d572-41cf-bbf4-11ebc1c0bc3b' }, + github: {user_id: 306015} + }, + repository: { + id: 138865824, + name: 'raulb/atleti', + type: 'github' + } + }) + kolkrabbiAPI.head('/source/archive/gAAAAABb') + .reply(200) + }) + .stub(git, 'readCommit', gitFake.readCommit) + .stub(git, 'githubRepository', gitFake.githubRepository) + .stub(git, 'createArchive', gitFake.createArchive) + .command(['ci:run', `--pipeline=${pipeline.name}`]) + .it('it runs the test and displays the test output for the first node', ({stdout}) => { + expect(stdout).to.equal('New Test setup outputNew Test output\n✓ #11 my-test-branch:668a5ce succeeded\n') + }) + }) +}) diff --git a/packages/ci/test/helpers/init.js b/packages/ci/test/helpers/init.js new file mode 100644 index 0000000000..f8e35e6cab --- /dev/null +++ b/packages/ci/test/helpers/init.js @@ -0,0 +1,2 @@ +const path = require('path') +process.env.TS_NODE_PROJECT = path.resolve('test/tsconfig.json') diff --git a/packages/ci/test/mocha.opts b/packages/ci/test/mocha.opts new file mode 100644 index 0000000000..ccc7f3491f --- /dev/null +++ b/packages/ci/test/mocha.opts @@ -0,0 +1,7 @@ +--require test/helpers/init.js +--require ts-node/register +--require source-map-support/register +--watch-extensions ts +--recursive +--reporter spec +--timeout 5000 diff --git a/packages/ci/test/tsconfig.json b/packages/ci/test/tsconfig.json new file mode 100644 index 0000000000..04c22f3bec --- /dev/null +++ b/packages/ci/test/tsconfig.json @@ -0,0 +1,11 @@ +{ + "declaration": false, + "extends": "../tsconfig", + "compilerOptions": { + "sourceMap": true + }, + "include": [ + "./**/*", + "../src/**/*" + ] +} diff --git a/packages/ci/tsconfig.json b/packages/ci/tsconfig.json new file mode 100644 index 0000000000..c6454f7a5f --- /dev/null +++ b/packages/ci/tsconfig.json @@ -0,0 +1,18 @@ +{ + "compilerOptions": { + "declaration": true, + "forceConsistentCasingInFileNames": true, + "importHelpers": true, + "module": "commonjs", + "outDir": "./lib", + "pretty": true, + "rootDirs": [ + "./src" + ], + "strict": true, + "target": "es2017" + }, + "include": [ + "./src/**/*" + ] +} diff --git a/packages/ci/tslint.json b/packages/ci/tslint.json new file mode 100644 index 0000000000..f5703540c9 --- /dev/null +++ b/packages/ci/tslint.json @@ -0,0 +1,3 @@ +{ + "extends": "@oclif/tslint" +} diff --git a/packages/cli/package.json b/packages/cli/package.json index c71143cf7a..067d49f19a 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -16,6 +16,7 @@ "@heroku-cli/plugin-autocomplete": "^7.7.4", "@heroku-cli/plugin-certs": "^7.5.9", "@heroku-cli/plugin-certs-v5": "^7.5.6", + "@heroku-cli/plugin-ci": "^0.0.0", "@heroku-cli/plugin-ci-v5": "^7.5.10", "@heroku-cli/plugin-config": "^7.5.9", "@heroku-cli/plugin-container-registry-v5": "^7.5.6", @@ -109,6 +110,7 @@ "@heroku-cli/plugin-certs", "@heroku-cli/plugin-certs-v5", "@heroku-cli/plugin-ci-v5", + "@heroku-cli/plugin-ci", "@heroku-cli/plugin-config", "@heroku-cli/plugin-container-registry-v5", "@heroku-cli/plugin-git", diff --git a/yarn.lock b/yarn.lock index 232de39334..8e2ae1a4f6 100644 --- a/yarn.lock +++ b/yarn.lock @@ -166,6 +166,10 @@ heroku-cli-util "^7.0.0" heroku-exec-util "0.7.2" +"@heroku-cli/schema@^1.0.12": + version "1.0.12" + resolved "https://registry.yarnpkg.com/@heroku-cli/schema/-/schema-1.0.12.tgz#f9d8f413a35160c3baebc0f6d3d63b8a9f531add" + "@heroku-cli/schema@^1.0.6": version "1.0.6" resolved "https://registry.yarnpkg.com/@heroku-cli/schema/-/schema-1.0.6.tgz#1f87b06e3126b1d89f952c0319b58ec580f01e4e" @@ -243,7 +247,7 @@ qqjs "^0.3.10" tslib "^1.9.2" -"@oclif/dev-cli@^1.15.4": +"@oclif/dev-cli@^1", "@oclif/dev-cli@^1.15.4": version "1.15.4" resolved "https://registry.yarnpkg.com/@oclif/dev-cli/-/dev-cli-1.15.4.tgz#ffd91e36adcb08dcecc7b8c905428ba0ca17bef3" dependencies: @@ -291,7 +295,7 @@ lodash "^4.17.10" tslib "^1.9.2" -"@oclif/plugin-help@2.0.5", "@oclif/plugin-help@^2.0.5": +"@oclif/plugin-help@2.0.5", "@oclif/plugin-help@^2", "@oclif/plugin-help@^2.0.5": version "2.0.5" resolved "https://registry.yarnpkg.com/@oclif/plugin-help/-/plugin-help-2.0.5.tgz#98084286099b44c8c6ed6214e3589f32525f4827" dependencies: @@ -452,6 +456,13 @@ "@types/minimatch" "*" "@types/node" "*" +"@types/inquirer@0.0.42": + version "0.0.42" + resolved "https://registry.yarnpkg.com/@types/inquirer/-/inquirer-0.0.42.tgz#2310fd8623053bead72247adae416aa32bacdf0c" + dependencies: + "@types/rx" "*" + "@types/through" "*" + "@types/lodash.flatten@^4.4.3": version "4.4.3" resolved "https://registry.yarnpkg.com/@types/lodash.flatten/-/lodash.flatten-4.4.3.tgz#7806caef7eca7aa75600b2f87c474e3af980304a" @@ -474,6 +485,10 @@ version "5.2.3" resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-5.2.3.tgz#11f3a5629d67cd444fa6c94536576244e6a52ea9" +"@types/mocha@^5": + version "5.2.5" + resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-5.2.5.tgz#8a4accfc403c124a0bafe8a9fc61a05ec1032073" + "@types/mocha@^5.2.2", "@types/mocha@^5.2.4": version "5.2.4" resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-5.2.4.tgz#2f8fbdf95c69ebf82150a7864864010f186745bf" @@ -492,6 +507,98 @@ version "10.3.6" resolved "https://registry.yarnpkg.com/@types/node/-/node-10.3.6.tgz#ea8aab9439b59f40d19ec5f13b44642344872b11" +"@types/node@^10": + version "10.5.5" + resolved "https://registry.yarnpkg.com/@types/node/-/node-10.5.5.tgz#8e84d24e896cd77b0d4f73df274027e3149ec2ba" + +"@types/rx-core-binding@*": + version "4.0.4" + resolved "https://registry.yarnpkg.com/@types/rx-core-binding/-/rx-core-binding-4.0.4.tgz#d969d32f15a62b89e2862c17b3ee78fe329818d3" + dependencies: + "@types/rx-core" "*" + +"@types/rx-core@*": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/rx-core/-/rx-core-4.0.3.tgz#0b3354b1238cedbe2b74f6326f139dbc7a591d60" + +"@types/rx-lite-aggregates@*": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/rx-lite-aggregates/-/rx-lite-aggregates-4.0.3.tgz#6efb2b7f3d5f07183a1cb2bd4b1371d7073384c2" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-async@*": + version "4.0.2" + resolved "https://registry.yarnpkg.com/@types/rx-lite-async/-/rx-lite-async-4.0.2.tgz#27fbf0caeff029f41e2d2aae638b05e91ceb600c" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-backpressure@*": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/rx-lite-backpressure/-/rx-lite-backpressure-4.0.3.tgz#05abb19bdf87cc740196c355e5d0b37bb50b5d56" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-coincidence@*": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/rx-lite-coincidence/-/rx-lite-coincidence-4.0.3.tgz#80bd69acc4054a15cdc1638e2dc8843498cd85c0" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-experimental@*": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@types/rx-lite-experimental/-/rx-lite-experimental-4.0.1.tgz#c532f5cbdf3f2c15da16ded8930d1b2984023cbd" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-joinpatterns@*": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@types/rx-lite-joinpatterns/-/rx-lite-joinpatterns-4.0.1.tgz#f70fe370518a8432f29158cc92ffb56b4e4afc3e" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-testing@*": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@types/rx-lite-testing/-/rx-lite-testing-4.0.1.tgz#21b19d11f4dfd6ffef5a9d1648e9c8879bfe21e9" + dependencies: + "@types/rx-lite-virtualtime" "*" + +"@types/rx-lite-time@*": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/rx-lite-time/-/rx-lite-time-4.0.3.tgz#0eda65474570237598f3448b845d2696f2dbb1c4" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite-virtualtime@*": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/rx-lite-virtualtime/-/rx-lite-virtualtime-4.0.3.tgz#4b30cacd0fe2e53af29f04f7438584c7d3959537" + dependencies: + "@types/rx-lite" "*" + +"@types/rx-lite@*": + version "4.0.5" + resolved "https://registry.yarnpkg.com/@types/rx-lite/-/rx-lite-4.0.5.tgz#b3581525dff69423798daa9a0d33c1e66a5e8c4c" + dependencies: + "@types/rx-core" "*" + "@types/rx-core-binding" "*" + +"@types/rx@*": + version "4.1.1" + resolved "https://registry.yarnpkg.com/@types/rx/-/rx-4.1.1.tgz#598fc94a56baed975f194574e0f572fd8e627a48" + dependencies: + "@types/rx-core" "*" + "@types/rx-core-binding" "*" + "@types/rx-lite" "*" + "@types/rx-lite-aggregates" "*" + "@types/rx-lite-async" "*" + "@types/rx-lite-backpressure" "*" + "@types/rx-lite-coincidence" "*" + "@types/rx-lite-experimental" "*" + "@types/rx-lite-joinpatterns" "*" + "@types/rx-lite-testing" "*" + "@types/rx-lite-time" "*" + "@types/rx-lite-virtualtime" "*" + "@types/semver@^5.5.0": version "5.5.0" resolved "https://registry.yarnpkg.com/@types/semver/-/semver-5.5.0.tgz#146c2a29ee7d3bae4bf2fcb274636e264c813c45" @@ -504,6 +611,16 @@ version "5.3.0" resolved "https://registry.yarnpkg.com/@types/supports-color/-/supports-color-5.3.0.tgz#eb6a52e9531fb3ebcd401cec774d1bdfb571f793" +"@types/through@*": + version "0.0.29" + resolved "https://registry.yarnpkg.com/@types/through/-/through-0.0.29.tgz#72943aac922e179339c651fa34a4428a4d722f93" + dependencies: + "@types/node" "*" + +"@types/validator@^9.4.1": + version "9.4.1" + resolved "https://registry.yarnpkg.com/@types/validator/-/validator-9.4.1.tgz#bea5a290e61f1cbf12af3fd878706aeec2ba0087" + "@types/write-json-file@^2.2.1": version "2.2.1" resolved "https://registry.yarnpkg.com/@types/write-json-file/-/write-json-file-2.2.1.tgz#74155aaccbb0d532be21f9d66bebc4ea875a5a62" @@ -738,6 +855,12 @@ assign-symbols@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/assign-symbols/-/assign-symbols-1.0.0.tgz#59667f41fadd4f20ccbc2bb96b8d4f7f78ec0367" +async-file@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/async-file/-/async-file-2.0.2.tgz#02ad07856ac3717e836b20aec5a4cfe00c46df23" + dependencies: + rimraf "^2.5.2" + async-limiter@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/async-limiter/-/async-limiter-1.0.0.tgz#78faed8c3d074ab81f22b4e985d79e8738f720f8" @@ -4007,7 +4130,7 @@ number-is-nan@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/number-is-nan/-/number-is-nan-1.0.1.tgz#097b602b53422a522c1afb8790318336941a011d" -nyc@12.0.2, nyc@^12.0.1, nyc@^12.0.2: +nyc@12.0.2, nyc@^12, nyc@^12.0.1, nyc@^12.0.2: version "12.0.2" resolved "https://registry.yarnpkg.com/nyc/-/nyc-12.0.2.tgz#8a4a4ed690966c11ec587ff87eea0c12c974ba99" dependencies: @@ -4717,7 +4840,7 @@ right-align@^0.1.1: dependencies: align-text "^0.1.1" -rimraf@^2.2.8, rimraf@^2.6.1, rimraf@^2.6.2: +rimraf@^2.2.8, rimraf@^2.5.2, rimraf@^2.6.1, rimraf@^2.6.2: version "2.6.2" resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.2.tgz#2ed8150d24a16ea8651e6d6ef0f47c4158ce7a36" dependencies: @@ -5503,6 +5626,19 @@ ts-node@7.0.0, ts-node@^7.0.0: source-map-support "^0.5.6" yn "^2.0.0" +ts-node@^6: + version "6.2.0" + resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-6.2.0.tgz#65a0ae2acce319ea4fd7ac8d7c9f1f90c5da6baf" + dependencies: + arrify "^1.0.0" + buffer-from "^1.1.0" + diff "^3.1.0" + make-error "^1.1.1" + minimist "^1.2.0" + mkdirp "^0.5.1" + source-map-support "^0.5.6" + yn "^2.0.0" + tslib@1.9.0: version "1.9.0" resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.9.0.tgz#e37a86fda8cbbaf23a057f473c9f4dc64e5fc2e8" @@ -5610,7 +5746,7 @@ typedarray@^0.0.6: version "0.0.6" resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" -typescript@2.9.2, typescript@^2.8, typescript@^2.8.3, typescript@^2.9.1, typescript@^2.9.2: +typescript@2.9.2, typescript@^2.8, typescript@^2.8.3, typescript@^2.9, typescript@^2.9.1, typescript@^2.9.2: version "2.9.2" resolved "https://registry.yarnpkg.com/typescript/-/typescript-2.9.2.tgz#1cbf61d05d6b96269244eb6a3bce4bd914e0f00c" @@ -5758,6 +5894,10 @@ validator@^10.2.0: version "10.4.0" resolved "https://registry.yarnpkg.com/validator/-/validator-10.4.0.tgz#ee99a44afb3bb5ed350a159f056ca72a204cfc3c" +validator@^10.5.0: + version "10.5.0" + resolved "https://registry.yarnpkg.com/validator/-/validator-10.5.0.tgz#1debbe1e6f5fd0c920ed2af47516f3762033939c" + walkdir@0.0.11: version "0.0.11" resolved "https://registry.yarnpkg.com/walkdir/-/walkdir-0.0.11.tgz#a16d025eb931bd03b52f308caed0f40fcebe9532" From 8f3e76e385228cfdae6580c4cb1c6a2a7707b691 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rau=CC=81l=20Barroso?= Date: Tue, 14 Aug 2018 18:00:10 +0200 Subject: [PATCH 6/6] v7.7.9 --- CHANGELOG.md | 9 +++ docs/access.md | 8 +-- docs/addons.md | 24 ++++---- docs/apps.md | 28 ++++----- docs/auth.md | 14 ++--- docs/autocomplete.md | 2 +- docs/buildpacks.md | 10 ++-- docs/certs.md | 26 ++++---- docs/ci.md | 89 ++++++++++++--------------- docs/config.md | 10 ++-- docs/container.md | 10 ++-- docs/domains.md | 10 ++-- docs/drains.md | 6 +- docs/features.md | 8 +-- docs/labs.md | 10 ++-- docs/logs.md | 2 +- docs/maintenance.md | 6 +- docs/notifications.md | 2 +- docs/pg.md | 88 +++++++++++++-------------- docs/pipelines.md | 10 ++-- docs/ps.md | 14 ++--- docs/psql.md | 2 +- docs/redis.md | 18 +++--- docs/releases.md | 8 +-- docs/run.md | 4 +- docs/spaces.md | 32 ++++++++++ docs/webhooks.md | 18 +++--- lerna.json | 2 +- packages/auth/CHANGELOG.md | 9 +++ packages/auth/README.md | 18 +++--- packages/auth/package.json | 2 +- packages/autocomplete/CHANGELOG.md | 12 ++++ packages/autocomplete/package.json | 2 +- packages/ci-v5/CHANGELOG.md | 9 +++ packages/ci-v5/package.json | 2 +- packages/ci/CHANGELOG.md | 9 +++ packages/ci/README.md | 96 +++++++++++++++++++++++++++++- packages/ci/package.json | 2 +- packages/cli/CHANGELOG.md | 9 +++ packages/cli/package.json | 12 ++-- packages/spaces/CHANGELOG.md | 9 +++ packages/spaces/README.md | 32 ++++++++++ packages/spaces/package.json | 2 +- 43 files changed, 453 insertions(+), 242 deletions(-) create mode 100644 packages/ci/CHANGELOG.md diff --git a/CHANGELOG.md b/CHANGELOG.md index 4d3ec7a911..c3e4fa0b9f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,15 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +## [7.7.9](https://github.com/heroku/cli/compare/v7.7.8...v7.7.9) (2018-08-14) + +**Note:** Version bump only for package heroku + + + + + ## [7.7.8](https://github.com/heroku/cli/compare/v7.7.7...v7.7.8) (2018-07-30) diff --git a/docs/access.md b/docs/access.md index a4d3df1840..4c6a267dcf 100644 --- a/docs/access.md +++ b/docs/access.md @@ -17,7 +17,7 @@ USAGE $ heroku access OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --json output in json format ``` @@ -31,7 +31,7 @@ USAGE $ heroku access:add EMAIL OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -p, --permissions=permissions list of permissions comma separated -r, --remote=remote git remote of app to use @@ -49,7 +49,7 @@ USAGE $ heroku access:remove EMAIL OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES @@ -65,7 +65,7 @@ USAGE $ heroku access:update EMAIL OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -p, --permissions=permissions comma-delimited list of permissions to update (deploy,manage,operate) -r, --remote=remote git remote of app to use diff --git a/docs/addons.md b/docs/addons.md index f4ec770933..b12a02858c 100644 --- a/docs/addons.md +++ b/docs/addons.md @@ -28,7 +28,7 @@ USAGE OPTIONS -A, --all show add-ons and attachments for all accessible apps - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --json return add-ons in json format @@ -52,7 +52,7 @@ USAGE $ heroku addons:attach ADDON_NAME OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --as=as name for add-on attachment --confirm=confirm overwrite existing add-on attachment with same name @@ -68,7 +68,7 @@ USAGE $ heroku addons:create SERVICE:PLAN OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --as=as name for the initial add-on attachment --confirm=confirm overwrite existing config vars or existing add-on attachments @@ -85,7 +85,7 @@ USAGE $ heroku addons:destroy [ADDON]... [flags] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -c, --confirm=confirm -f, --force allow destruction even if connected to other apps -r, --remote=remote git remote of app to use @@ -100,7 +100,7 @@ USAGE $ heroku addons:detach ATTACHMENT_NAME OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -113,7 +113,7 @@ USAGE $ heroku addons:docs ADDON OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --show-url show URL, do not open browser ``` @@ -127,7 +127,7 @@ USAGE $ heroku addons:downgrade ADDON [PLAN] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -155,7 +155,7 @@ USAGE $ heroku addons:info ADDON OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use ``` @@ -168,7 +168,7 @@ USAGE $ heroku addons:open ADDON OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --show-url show URL, do not open browser ``` @@ -194,7 +194,7 @@ USAGE $ heroku addons:rename ADDON NEW_NAME OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use ``` @@ -219,7 +219,7 @@ USAGE $ heroku addons:upgrade ADDON [PLAN] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -247,7 +247,7 @@ USAGE $ heroku addons:wait ADDON OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --wait-interval=wait-interval how frequently to poll in seconds ``` diff --git a/docs/apps.md b/docs/apps.md index 058f7c9296..d8e2932436 100644 --- a/docs/apps.md +++ b/docs/apps.md @@ -102,7 +102,7 @@ USAGE $ heroku apps:destroy OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use @@ -119,7 +119,7 @@ USAGE $ heroku apps:errors OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --dyno show only dyno errors --hours=hours number of hours to look back (default 24) @@ -148,7 +148,7 @@ USAGE $ heroku apps:favorites:add OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -161,7 +161,7 @@ USAGE $ heroku apps:favorites:remove OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -174,7 +174,7 @@ USAGE $ heroku apps:info OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -j, --json -r, --remote=remote git remote of app to use -s, --shell output more shell friendly key/value pairs @@ -201,7 +201,7 @@ USAGE $ heroku apps:join OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -214,7 +214,7 @@ USAGE $ heroku apps:leave OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -227,7 +227,7 @@ USAGE $ heroku apps:lock OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -240,7 +240,7 @@ USAGE $ heroku apps:open [PATH] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES @@ -260,7 +260,7 @@ USAGE $ heroku apps:rename NEWNAME OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --ssh-git use ssh git protocol instead of https @@ -282,7 +282,7 @@ USAGE $ heroku apps:stacks OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -295,7 +295,7 @@ USAGE $ heroku apps:stacks:set STACK OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES @@ -316,7 +316,7 @@ ARGUMENTS RECIPIENT user or team to transfer applications to OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -l, --locked lock the app upon transfer -r, --remote=remote git remote of app to use --bulk transfer applications in bulk @@ -341,6 +341,6 @@ USAGE $ heroku apps:unlock OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` diff --git a/docs/auth.md b/docs/auth.md index 4695dc754c..1cefa3c287 100644 --- a/docs/auth.md +++ b/docs/auth.md @@ -24,7 +24,7 @@ ALIASES $ heroku twofactor ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/2fa/index.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/2fa/index.ts)_ ## `heroku auth:2fa:disable` @@ -43,7 +43,7 @@ EXAMPLES Disabling 2fa on me@example.com... done ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/2fa/disable.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/2fa/disable.ts)_ ## `heroku auth:2fa:generate-recovery-codes` @@ -82,7 +82,7 @@ EXAMPLES f82e7c2a50737494 ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/2fa/generate-recovery-codes.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/2fa/generate-recovery-codes.ts)_ ## `heroku auth:login` @@ -102,7 +102,7 @@ ALIASES $ heroku login ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/login.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/login.ts)_ ## `heroku auth:logout` @@ -116,7 +116,7 @@ ALIASES $ heroku logout ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/logout.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/logout.ts)_ ## `heroku auth:token` @@ -134,7 +134,7 @@ DESCRIPTION authorizations:create ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/token.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/token.ts)_ ## `heroku auth:whoami` @@ -148,4 +148,4 @@ ALIASES $ heroku whoami ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/whoami.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/whoami.ts)_ diff --git a/docs/autocomplete.md b/docs/autocomplete.md index a2a04c3143..e3f500f733 100644 --- a/docs/autocomplete.md +++ b/docs/autocomplete.md @@ -26,4 +26,4 @@ EXAMPLES $ heroku autocomplete --refresh-cache ``` -_See code: [@heroku-cli/plugin-autocomplete](https://github.com/heroku/heroku-cli-autocomplete/blob/v7.7.4/src/commands/autocomplete/index.ts)_ +_See code: [@heroku-cli/plugin-autocomplete](https://github.com/heroku/heroku-cli-autocomplete/blob/v7.7.9/src/commands/autocomplete/index.ts)_ diff --git a/docs/buildpacks.md b/docs/buildpacks.md index 90c8d88bec..a0d212355e 100644 --- a/docs/buildpacks.md +++ b/docs/buildpacks.md @@ -18,7 +18,7 @@ USAGE $ heroku buildpacks OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES @@ -36,7 +36,7 @@ USAGE $ heroku buildpacks:add URL OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -i, --index=index the 1-based index of the URL in the list of URLs -r, --remote=remote git remote of app to use @@ -53,7 +53,7 @@ USAGE $ heroku buildpacks:clear OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -66,7 +66,7 @@ USAGE $ heroku buildpacks:remove [URL] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -i, --index=index the 1-based index of the URL to remove from the list of URLs -r, --remote=remote git remote of app to use ``` @@ -80,7 +80,7 @@ USAGE $ heroku buildpacks:set URL OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -i, --index=index the 1-based index of the URL in the list of URLs -r, --remote=remote git remote of app to use diff --git a/docs/certs.md b/docs/certs.md index e8700f3cb7..012a6318a5 100644 --- a/docs/certs.md +++ b/docs/certs.md @@ -26,7 +26,7 @@ USAGE $ heroku certs OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -41,7 +41,7 @@ USAGE $ heroku certs:add CRT KEY OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --bypass bypass the trust chain completion step --domains=domains domains to create after certificate upload @@ -68,7 +68,7 @@ USAGE $ heroku certs:auto OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -83,7 +83,7 @@ USAGE $ heroku certs:auto:disable OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -98,7 +98,7 @@ USAGE $ heroku certs:auto:enable OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -113,7 +113,7 @@ USAGE $ heroku certs:auto:refresh OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -128,7 +128,7 @@ USAGE $ heroku certs:chain OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -143,7 +143,7 @@ USAGE $ heroku certs:generate DOMAIN OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --area=area sub-country area (state, province, etc.) of owner --city=city city of owner @@ -175,7 +175,7 @@ USAGE $ heroku certs:info OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --endpoint=endpoint endpoint to check info on --name=name name to check info on @@ -192,7 +192,7 @@ USAGE $ heroku certs:key OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -214,7 +214,7 @@ USAGE $ heroku certs:remove OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --endpoint=endpoint endpoint to remove --name=name name to remove @@ -231,7 +231,7 @@ USAGE $ heroku certs:rollback OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --endpoint=endpoint endpoint to rollback --name=name name to rollback @@ -248,7 +248,7 @@ USAGE $ heroku certs:update CRT KEY OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --bypass bypass the trust chain completion step --endpoint=endpoint endpoint to update diff --git a/docs/ci.md b/docs/ci.md index 54b28bc8f7..3de0446065 100644 --- a/docs/ci.md +++ b/docs/ci.md @@ -9,7 +9,7 @@ run an application test suite on Heroku * [`heroku ci:config:set`](#heroku-ciconfigset) * [`heroku ci:config:unset`](#heroku-ciconfigunset) * [`heroku ci:debug`](#heroku-cidebug) -* [`heroku ci:info NUMBER`](#heroku-ciinfo-number) +* [`heroku ci:info TEST-RUN`](#heroku-ciinfo-test-run) * [`heroku ci:last`](#heroku-cilast) * [`heroku ci:migrate-manifest`](#heroku-cimigrate-manifest) * [`heroku ci:open`](#heroku-ciopen) @@ -25,7 +25,7 @@ USAGE $ heroku ci OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -j, --json output run info in json format -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use @@ -48,7 +48,7 @@ USAGE $ heroku ci:config OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use -s, --shell output config vars in shell format @@ -69,7 +69,7 @@ USAGE $ heroku ci:config:get KEY OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use -s, --shell output config var in shell format @@ -90,7 +90,7 @@ USAGE $ heroku ci:config:set OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use @@ -112,7 +112,7 @@ USAGE $ heroku ci:config:unset OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use @@ -132,7 +132,7 @@ USAGE $ heroku ci:debug OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use --no-cache start test run with an empty cache @@ -149,51 +149,44 @@ DESCRIPTION ~ $ ``` -## `heroku ci:info NUMBER` +## `heroku ci:info TEST-RUN` -test run information +show the status of a specific test run ``` USAGE - $ heroku ci:info NUMBER - -ARGUMENTS - NUMBER the test run number to show + $ heroku ci:info TEST-RUN OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against - -p, --pipeline=pipeline pipeline - -r, --remote=remote git remote of app to use - -DESCRIPTION - show the status of a specific test run - - Example: + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline + --node=node the node number to show its setup and output - $ heroku ci:info 1288 --app murmuring-headland-14719 +EXAMPLE + $ heroku ci:info 1288 --app murmuring-headland-14719 ``` +_See code: [@heroku-cli/plugin-ci](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/info.ts)_ + ## `heroku ci:last` -get the results of the last run +looks for the most recent run and returns the output of that run ``` USAGE $ heroku ci:last OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against - -p, --pipeline=pipeline pipeline - -r, --remote=remote git remote of app to use - -DESCRIPTION - looks for the most recent run and returns the output of that run + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline + --node=node the node number to show its setup and output - Example: - - $ heroku ci:last --app murmuring-headland-14719 +EXAMPLE + $ heroku ci:last --app murmuring-headland-14719 --node 100 ``` +_See code: [@heroku-cli/plugin-ci](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/last.ts)_ + ## `heroku ci:migrate-manifest` app-ci.json is deprecated. Run this command to migrate to app.json with an environments key. @@ -221,7 +214,7 @@ USAGE $ heroku ci:open OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -p, --pipeline=pipeline pipeline -r, --remote=remote git remote of app to use @@ -242,18 +235,15 @@ USAGE $ heroku ci:rerun [NUMBER] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against - -p, --pipeline=pipeline pipeline - -r, --remote=remote git remote of app to use - -DESCRIPTION - uploads the contents of the current directory, using git archive, to Heroku and runs the tests + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline - Example: - - $ heroku ci:rerun 985 --app murmuring-headland-14719 +EXAMPLE + $ heroku ci:rerun 985 --app murmuring-headland-14719 ``` +_See code: [@heroku-cli/plugin-ci](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/rerun.ts)_ + ## `heroku ci:run` run tests against current directory @@ -263,14 +253,11 @@ USAGE $ heroku ci:run OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against - -p, --pipeline=pipeline pipeline - -r, --remote=remote git remote of app to use - -DESCRIPTION - uploads the contents of the current directory to Heroku and runs the tests + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline - Example: - - $ heroku ci:run --app murmuring-headland-14719 +EXAMPLE + $ heroku ci:run --app murmuring-headland-14719 ``` + +_See code: [@heroku-cli/plugin-ci](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/run.ts)_ diff --git a/docs/config.md b/docs/config.md index fa918c6026..59ee2a93c4 100644 --- a/docs/config.md +++ b/docs/config.md @@ -18,7 +18,7 @@ USAGE $ heroku config OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -j, --json output config vars in json format -r, --remote=remote git remote of app to use -s, --shell output config vars in shell format @@ -38,7 +38,7 @@ ARGUMENTS KEY edit a single key OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -67,7 +67,7 @@ USAGE $ heroku config:get KEY... OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -s, --shell output config vars in shell format @@ -87,7 +87,7 @@ USAGE $ heroku config:set OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES @@ -110,7 +110,7 @@ USAGE $ heroku config:unset OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ALIASES diff --git a/docs/container.md b/docs/container.md index f52e04c233..c9951e6154 100644 --- a/docs/container.md +++ b/docs/container.md @@ -58,7 +58,7 @@ USAGE $ heroku container:pull OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -v, --verbose @@ -79,7 +79,7 @@ USAGE OPTIONS -R, --recursive pushes Dockerfile. found in current and subdirectories - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -v, --verbose --arg=arg set build-time variables @@ -103,7 +103,7 @@ USAGE $ heroku container:release OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -v, --verbose @@ -122,7 +122,7 @@ USAGE $ heroku container:rm OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -140,7 +140,7 @@ USAGE $ heroku container:run OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -p, --port=port port the app will run on -r, --remote=remote git remote of app to use -v, --verbose diff --git a/docs/domains.md b/docs/domains.md index 940694333d..63760cdace 100644 --- a/docs/domains.md +++ b/docs/domains.md @@ -18,7 +18,7 @@ USAGE $ heroku domains OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --json output in json format @@ -42,7 +42,7 @@ USAGE $ heroku domains:add HOSTNAME OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --wait ``` @@ -56,7 +56,7 @@ USAGE $ heroku domains:clear OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -69,7 +69,7 @@ USAGE $ heroku domains:remove HOSTNAME OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -82,6 +82,6 @@ USAGE $ heroku domains:wait [HOSTNAME] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` diff --git a/docs/drains.md b/docs/drains.md index b0aa6031f7..9de373331e 100644 --- a/docs/drains.md +++ b/docs/drains.md @@ -16,7 +16,7 @@ USAGE $ heroku drains OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --json output in json format ``` @@ -30,7 +30,7 @@ USAGE $ heroku drains:add URL OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -43,6 +43,6 @@ USAGE $ heroku drains:remove [URL|TOKEN] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` diff --git a/docs/features.md b/docs/features.md index 4716b4341e..b8dfcb0fa5 100644 --- a/docs/features.md +++ b/docs/features.md @@ -17,7 +17,7 @@ USAGE $ heroku features OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --json output in json format ``` @@ -31,7 +31,7 @@ USAGE $ heroku features:disable FEATURE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -44,7 +44,7 @@ USAGE $ heroku features:enable FEATURE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -57,7 +57,7 @@ USAGE $ heroku features:info FEATURE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --json output in json format ``` diff --git a/docs/labs.md b/docs/labs.md index d11cf33921..90d3ad058c 100644 --- a/docs/labs.md +++ b/docs/labs.md @@ -17,7 +17,7 @@ USAGE $ heroku labs OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --json display as json ``` @@ -31,12 +31,12 @@ USAGE $ heroku labs:disable [FEATURE] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --confirm=confirm ``` -_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/labs/disable.ts)_ +_See code: [@heroku-cli/plugin-auth](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/labs/disable.ts)_ ## `heroku labs:enable FEATURE` @@ -47,7 +47,7 @@ USAGE $ heroku labs:enable FEATURE OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use ``` @@ -60,7 +60,7 @@ USAGE $ heroku labs:info FEATURE OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --json display as json ``` diff --git a/docs/logs.md b/docs/logs.md index 2025fc3c5b..7fff9594cc 100644 --- a/docs/logs.md +++ b/docs/logs.md @@ -14,7 +14,7 @@ USAGE $ heroku logs OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -d, --dyno=dyno only show output from this dyno type (such as "web" or "worker") -n, --num=num number of lines to display -r, --remote=remote git remote of app to use diff --git a/docs/maintenance.md b/docs/maintenance.md index aeaf7f6a70..5e0f6042e6 100644 --- a/docs/maintenance.md +++ b/docs/maintenance.md @@ -16,7 +16,7 @@ USAGE $ heroku maintenance OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -29,7 +29,7 @@ USAGE $ heroku maintenance:off OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -42,6 +42,6 @@ USAGE $ heroku maintenance:on OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` diff --git a/docs/notifications.md b/docs/notifications.md index ec17a65076..7c23bea1cc 100644 --- a/docs/notifications.md +++ b/docs/notifications.md @@ -14,7 +14,7 @@ USAGE $ heroku notifications OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --all view all notifications (not just the ones for the current app) --json output in json format diff --git a/docs/pg.md b/docs/pg.md index cc7f445313..3a5b6aae40 100644 --- a/docs/pg.md +++ b/docs/pg.md @@ -57,7 +57,7 @@ USAGE $ heroku pg [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -70,7 +70,7 @@ USAGE $ heroku pg:backups OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -83,7 +83,7 @@ USAGE $ heroku pg:backups:cancel [BACKUP_ID] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -96,7 +96,7 @@ USAGE $ heroku pg:backups:capture [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -v, --verbose --snapshot @@ -112,7 +112,7 @@ USAGE $ heroku pg:backups:delete BACKUP_ID OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use ``` @@ -126,7 +126,7 @@ USAGE $ heroku pg:backups:download [BACKUP_ID] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -o, --output=output location to download to. Defaults to latest.dump -r, --remote=remote git remote of app to use ``` @@ -140,7 +140,7 @@ USAGE $ heroku pg:backups:info [BACKUP_ID] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -153,7 +153,7 @@ USAGE $ heroku pg:backups:restore [BACKUP] [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use -v, --verbose @@ -172,7 +172,7 @@ USAGE $ heroku pg:backups:schedule [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --at=at (required) at a specific (24h) hour in the given timezone. Defaults to UTC. --at '[HOUR]:00 @@ -188,7 +188,7 @@ USAGE $ heroku pg:backups:schedules OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -201,7 +201,7 @@ USAGE $ heroku pg:backups:unschedule [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -214,7 +214,7 @@ USAGE $ heroku pg:backups:url [BACKUP_ID] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -227,7 +227,7 @@ USAGE $ heroku pg:connection-pooling:attach [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -n, --credential=credential name of the credential within the database -r, --remote=remote git remote of app to use --as=as name for add-on attachment @@ -247,7 +247,7 @@ USAGE $ heroku pg:copy SOURCE TARGET OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --confirm=confirm --verbose @@ -266,7 +266,7 @@ USAGE $ heroku pg:credentials [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --reset DEPRECATED ``` @@ -280,7 +280,7 @@ USAGE $ heroku pg:credentials:create [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -n, --name=name (required) name of the new credential within the database -r, --remote=remote git remote of app to use @@ -299,7 +299,7 @@ USAGE $ heroku pg:credentials:destroy [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -n, --name=name (required) unique identifier for the credential -r, --remote=remote git remote of app to use @@ -319,7 +319,7 @@ USAGE $ heroku pg:credentials:repair-default [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use @@ -338,7 +338,7 @@ USAGE $ heroku pg:credentials:rotate [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -n, --name=name which credential to rotate (default credentials if not specified) -r, --remote=remote git remote of app to use @@ -355,7 +355,7 @@ USAGE $ heroku pg:credentials:url [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -n, --name=name which credential to show (default credentials if not specified) -r, --remote=remote git remote of app to use ``` @@ -369,7 +369,7 @@ USAGE $ heroku pg:diagnose [DATABASE|REPORT_ID] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -386,7 +386,7 @@ USAGE $ heroku pg:info [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -399,7 +399,7 @@ USAGE $ heroku pg:kill PID [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -f, --force -r, --remote=remote git remote of app to use ``` @@ -413,7 +413,7 @@ USAGE $ heroku pg:killall [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -426,7 +426,7 @@ USAGE $ heroku pg:links [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -439,7 +439,7 @@ USAGE $ heroku pg:links:create REMOTE DATABASE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --as=as name of link to create @@ -458,7 +458,7 @@ USAGE $ heroku pg:links:destroy DATABASE LINK OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use @@ -477,7 +477,7 @@ USAGE $ heroku pg:maintenance [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -490,7 +490,7 @@ USAGE $ heroku pg:maintenance:run [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -f, --force -r, --remote=remote git remote of app to use ``` @@ -504,7 +504,7 @@ USAGE $ heroku pg:maintenance:window DATABASE WINDOW OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -524,7 +524,7 @@ USAGE $ heroku pg:outliers [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -n, --num=num the number of queries to display (default: 10) -r, --remote=remote git remote of app to use -t, --truncate truncate queries to 40 characters @@ -540,7 +540,7 @@ USAGE $ heroku pg:promote DATABASE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -553,7 +553,7 @@ USAGE $ heroku pg:ps [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -v, --verbose ``` @@ -567,7 +567,7 @@ USAGE $ heroku pg:psql [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --command=command SQL command to run -f, --file=file SQL file to run -r, --remote=remote git remote of app to use @@ -583,7 +583,7 @@ USAGE $ heroku pg:pull SOURCE TARGET OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --exclude-table-data=exclude-table-data tables for which data should be excluded (use ';' to split multiple names) @@ -617,7 +617,7 @@ USAGE $ heroku pg:push SOURCE TARGET OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --exclude-table-data=exclude-table-data tables for which data should be excluded (use ';' to split multiple names) @@ -647,7 +647,7 @@ USAGE $ heroku pg:reset [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use ``` @@ -661,7 +661,7 @@ USAGE $ heroku pg:settings [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -674,7 +674,7 @@ USAGE $ heroku pg:settings:log-lock-waits [VALUE] [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -693,7 +693,7 @@ USAGE $ heroku pg:settings:log-min-duration-statement [VALUE] [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -711,7 +711,7 @@ USAGE $ heroku pg:settings:log-statement [VALUE] [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -732,7 +732,7 @@ USAGE $ heroku pg:unfollow DATABASE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use ``` @@ -746,7 +746,7 @@ USAGE $ heroku pg:upgrade [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use -v, --version=version PostgreSQL version to upgrade to @@ -764,7 +764,7 @@ USAGE $ heroku pg:wait [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --no-notify do not show OS notification --wait-interval=wait-interval how frequently to poll in seconds (to avoid rate limiting) diff --git a/docs/pipelines.md b/docs/pipelines.md index b7ad3f9af2..fabf93666f 100644 --- a/docs/pipelines.md +++ b/docs/pipelines.md @@ -48,7 +48,7 @@ ARGUMENTS PIPELINE name of pipeline OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -s, --stage=stage stage of first app in pipeline @@ -92,7 +92,7 @@ ARGUMENTS NAME name of pipeline, defaults to basename of app OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -s, --stage=stage stage of first app in pipeline -t, --team=team team to use @@ -136,7 +136,7 @@ USAGE $ heroku pipelines:diff OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES @@ -214,7 +214,7 @@ USAGE $ heroku pipelines:promote OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -t, --to=to comma separated list of apps to promote to @@ -240,7 +240,7 @@ USAGE $ heroku pipelines:remove OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use EXAMPLES diff --git a/docs/ps.md b/docs/ps.md index 6dfabf9906..756e5003b6 100644 --- a/docs/ps.md +++ b/docs/ps.md @@ -24,7 +24,7 @@ USAGE $ heroku ps [TYPE [TYPE ...]] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --json display as json @@ -111,7 +111,7 @@ USAGE $ heroku ps:kill DYNO OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -134,7 +134,7 @@ USAGE $ heroku ps:resize OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -155,7 +155,7 @@ USAGE $ heroku ps:restart [DYNO] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -181,7 +181,7 @@ USAGE $ heroku ps:scale OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -229,7 +229,7 @@ USAGE $ heroku ps:stop DYNO OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION @@ -252,7 +252,7 @@ USAGE $ heroku ps:type OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION diff --git a/docs/psql.md b/docs/psql.md index 37ed18a0e6..0da62a25a8 100644 --- a/docs/psql.md +++ b/docs/psql.md @@ -14,7 +14,7 @@ USAGE $ heroku psql [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --command=command SQL command to run -f, --file=file SQL file to run -r, --remote=remote git remote of app to use diff --git a/docs/redis.md b/docs/redis.md index 90385a025e..3fcf2cd3c9 100644 --- a/docs/redis.md +++ b/docs/redis.md @@ -22,7 +22,7 @@ USAGE $ heroku redis [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -35,7 +35,7 @@ USAGE $ heroku redis:cli [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -c, --confirm=confirm -r, --remote=remote git remote of app to use ``` @@ -49,7 +49,7 @@ USAGE $ heroku redis:credentials [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use --reset reset credentials ``` @@ -63,7 +63,7 @@ USAGE $ heroku redis:info [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -76,7 +76,7 @@ USAGE $ heroku redis:maintenance [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -f, --force start maintenance without entering application maintenance mode -r, --remote=remote git remote of app to use -w, --window=window set weekly UTC maintenance window @@ -95,7 +95,7 @@ USAGE $ heroku redis:maxmemory [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -p, --policy=policy (required) set policy name -r, --remote=remote git remote of app to use @@ -119,7 +119,7 @@ USAGE $ heroku redis:promote DATABASE OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -132,7 +132,7 @@ USAGE $ heroku redis:timeout [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -s, --seconds=seconds set timeout value @@ -150,6 +150,6 @@ USAGE $ heroku redis:wait [DATABASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` diff --git a/docs/releases.md b/docs/releases.md index 2b5c14484e..a6903c6f9b 100644 --- a/docs/releases.md +++ b/docs/releases.md @@ -17,7 +17,7 @@ USAGE $ heroku releases OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -n, --num=num number of releases to show -r, --remote=remote git remote of app to use --json output releases in json format @@ -39,7 +39,7 @@ USAGE $ heroku releases:info [RELEASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use -s, --shell output in shell format --json output in json format @@ -54,7 +54,7 @@ USAGE $ heroku releases:output [RELEASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use ``` @@ -67,7 +67,7 @@ USAGE $ heroku releases:rollback [RELEASE] OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -r, --remote=remote git remote of app to use DESCRIPTION diff --git a/docs/run.md b/docs/run.md index 93f194faa3..31ac4c88a5 100644 --- a/docs/run.md +++ b/docs/run.md @@ -15,7 +15,7 @@ USAGE $ heroku run OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -e, --env=env environment variables to set (use ';' to split multiple vars) -r, --remote=remote git remote of app to use -s, --size=size dyno size @@ -47,7 +47,7 @@ USAGE $ heroku run:detached OPTIONS - -a, --app=app (required) [default: safe-sea-44297] app to run command against + -a, --app=app (required) app to run command against -e, --env=env environment variables to set (use ';' to split multiple vars) -r, --remote=remote git remote of app to use -s, --size=size dyno size diff --git a/docs/spaces.md b/docs/spaces.md index e0dd61996e..3e3ab190e4 100644 --- a/docs/spaces.md +++ b/docs/spaces.md @@ -14,6 +14,7 @@ manage heroku private spaces * [`heroku spaces:ps`](#heroku-spacesps) * [`heroku spaces:rename`](#heroku-spacesrename) * [`heroku spaces:topology`](#heroku-spacestopology) +* [`heroku spaces:vpn:config`](#heroku-spacesvpnconfig) * [`heroku spaces:vpn:connect`](#heroku-spacesvpnconnect) * [`heroku spaces:vpn:connections`](#heroku-spacesvpnconnections) * [`heroku spaces:vpn:destroy`](#heroku-spacesvpndestroy) @@ -226,6 +227,37 @@ OPTIONS --json output in json format ``` +## `heroku spaces:vpn:config` + +display the configuration information for VPN + +``` +USAGE + $ heroku spaces:vpn:config + +OPTIONS + -n, --name=name name or id of the VPN connection to retrieve config from + -s, --space=space space the VPN connection belongs to + --json output in json format + +DESCRIPTION + Example: + + $ heroku spaces:vpn:config --space my-space vpn-connection-name + === vpn-connection-name VPN Tunnels + VPN Tunnel Customer Gateway VPN Gateway Pre-shared Key Routable Subnets IKE Version + ────────── ──────────────── ────────────── ────────────── ──────────────── ─────────── + Tunnel 1 104.196.121.200 35.171.237.136 abcdef12345 10.0.0.0/16 1 + Tunnel 2 104.196.121.200 52.44.7.216 fedcba54321 10.0.0.0/16 1 + + You will use the information provided by this command to establish a Private Space VPN Connection. + + - You must configure your VPN Gateway to use both Tunnels provided by Heroku + - The VPN Gateway values are the IP addresses of the Private Space Tunnels + - The Customer Gateway value is the Public IP of your VPN Gateway + - The VPN Gateway must use the IKE Version shown and the Pre-shared Keys as the authentication method +``` + ## `heroku spaces:vpn:connect` create VPN diff --git a/docs/webhooks.md b/docs/webhooks.md index af23b86e46..c82b2862b4 100644 --- a/docs/webhooks.md +++ b/docs/webhooks.md @@ -22,7 +22,7 @@ USAGE $ heroku webhooks OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against EXAMPLE $ heroku webhooks @@ -39,7 +39,7 @@ USAGE $ heroku webhooks:add OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -i, --include=include (required) comma delimited event types your server will receive -l, --level=level (required) notify does not retry, sync will retry until successful or timeout -s, --secret=secret value to sign delivery with in Heroku-Webhook-Hmac-SHA256 header @@ -61,7 +61,7 @@ USAGE $ heroku webhooks:deliveries OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -s, --status=status filter deliveries by status EXAMPLE @@ -79,7 +79,7 @@ USAGE $ heroku webhooks:deliveries:info [ID] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against EXAMPLE $ heroku webhooks:deliveries:info 99999999-9999-9999-9999-999999999999 @@ -96,7 +96,7 @@ USAGE $ heroku webhooks:events OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against EXAMPLE $ heroku webhooks:events @@ -113,7 +113,7 @@ USAGE $ heroku webhooks:events:info [ID] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against EXAMPLE $ heroku webhooks:events:info 99999999-9999-9999-9999-999999999999 @@ -130,7 +130,7 @@ USAGE $ heroku webhooks:info [ID] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against EXAMPLE $ heroku webhooks:info 99999999-9999-9999-9999-999999999999 @@ -150,7 +150,7 @@ ARGUMENTS ID id of webhook to remove OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against EXAMPLE $ heroku webhooks:remove 99999999-9999-9999-9999-999999999999 @@ -167,7 +167,7 @@ USAGE $ heroku webhooks:update [ID] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -i, --include=include (required) comma delimited event types your server will receive -l, --level=level (required) notify does not retry, sync will retry until successful or timeout -s, --secret=secret value to sign delivery with in Heroku-Webhook-Hmac-SHA256 header diff --git a/lerna.json b/lerna.json index e5a0a4a3af..afdc2115a2 100644 --- a/lerna.json +++ b/lerna.json @@ -1,5 +1,5 @@ { - "version": "7.7.8", + "version": "7.7.9", "lerna": "2.11.0", "useWorkspaces": true, "npmClient": "yarn", diff --git a/packages/auth/CHANGELOG.md b/packages/auth/CHANGELOG.md index 0610cf8cc7..b9deccf8fd 100644 --- a/packages/auth/CHANGELOG.md +++ b/packages/auth/CHANGELOG.md @@ -3,6 +3,15 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +## [7.7.9](https://github.com/heroku/cli/compare/v7.7.8...v7.7.9) (2018-08-14) + +**Note:** Version bump only for package @heroku-cli/plugin-auth + + + + + ## [7.5.9](https://github.com/heroku/cli/compare/v7.5.8...v7.5.9) (2018-07-02) diff --git a/packages/auth/README.md b/packages/auth/README.md index bc87980787..00d29b4345 100644 --- a/packages/auth/README.md +++ b/packages/auth/README.md @@ -37,7 +37,7 @@ ALIASES $ heroku twofactor ``` -_See code: [src/commands/auth/2fa/index.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/2fa/index.ts)_ +_See code: [src/commands/auth/2fa/index.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/2fa/index.ts)_ ## `heroku auth:2fa:disable` @@ -56,7 +56,7 @@ EXAMPLES Disabling 2fa on me@example.com... done ``` -_See code: [src/commands/auth/2fa/disable.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/2fa/disable.ts)_ +_See code: [src/commands/auth/2fa/disable.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/2fa/disable.ts)_ ## `heroku auth:2fa:generate-recovery-codes` @@ -95,7 +95,7 @@ EXAMPLES f82e7c2a50737494 ``` -_See code: [src/commands/auth/2fa/generate-recovery-codes.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/2fa/generate-recovery-codes.ts)_ +_See code: [src/commands/auth/2fa/generate-recovery-codes.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/2fa/generate-recovery-codes.ts)_ ## `heroku auth:login` @@ -115,7 +115,7 @@ ALIASES $ heroku login ``` -_See code: [src/commands/auth/login.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/login.ts)_ +_See code: [src/commands/auth/login.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/login.ts)_ ## `heroku auth:logout` @@ -129,7 +129,7 @@ ALIASES $ heroku logout ``` -_See code: [src/commands/auth/logout.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/logout.ts)_ +_See code: [src/commands/auth/logout.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/logout.ts)_ ## `heroku auth:token` @@ -147,7 +147,7 @@ DESCRIPTION authorizations:create ``` -_See code: [src/commands/auth/token.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/token.ts)_ +_See code: [src/commands/auth/token.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/token.ts)_ ## `heroku auth:whoami` @@ -161,7 +161,7 @@ ALIASES $ heroku whoami ``` -_See code: [src/commands/auth/whoami.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/auth/whoami.ts)_ +_See code: [src/commands/auth/whoami.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/auth/whoami.ts)_ ## `heroku labs:disable [FEATURE]` @@ -172,10 +172,10 @@ USAGE $ heroku labs:disable [FEATURE] OPTIONS - -a, --app=app [default: safe-sea-44297] app to run command against + -a, --app=app app to run command against -r, --remote=remote git remote of app to use --confirm=confirm ``` -_See code: [src/commands/labs/disable.ts](https://github.com/heroku/cli/blob/v7.5.9/packages/auth/src/commands/labs/disable.ts)_ +_See code: [src/commands/labs/disable.ts](https://github.com/heroku/cli/blob/v7.7.9/packages/auth/src/commands/labs/disable.ts)_ diff --git a/packages/auth/package.json b/packages/auth/package.json index add89b47bc..1c65e4f27b 100644 --- a/packages/auth/package.json +++ b/packages/auth/package.json @@ -1,7 +1,7 @@ { "name": "@heroku-cli/plugin-auth", "description": "auth core plugin for Heroku CLI", - "version": "7.5.9", + "version": "7.7.9", "author": "Jeff Dickey @jdxcode", "bugs": "https://github.com/heroku/cli/issues", "dependencies": { diff --git a/packages/autocomplete/CHANGELOG.md b/packages/autocomplete/CHANGELOG.md index eabc44192f..440a5d2245 100644 --- a/packages/autocomplete/CHANGELOG.md +++ b/packages/autocomplete/CHANGELOG.md @@ -3,6 +3,18 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +## [7.7.9](https://github.com/heroku/heroku-cli-autocomplete/compare/v7.7.8...v7.7.9) (2018-08-14) + + +### Bug Fixes + +* **autocomplete:** filepath completions ([#968](https://github.com/heroku/heroku-cli-autocomplete/issues/968)) ([b681eb5](https://github.com/heroku/heroku-cli-autocomplete/commit/b681eb5)) + + + + + ## [7.7.4](https://github.com/heroku/heroku-cli-autocomplete/compare/v7.7.3...v7.7.4) (2018-07-19) diff --git a/packages/autocomplete/package.json b/packages/autocomplete/package.json index d80741c6d8..944765aad8 100644 --- a/packages/autocomplete/package.json +++ b/packages/autocomplete/package.json @@ -1,6 +1,6 @@ { "name": "@heroku-cli/plugin-autocomplete", - "version": "7.7.4", + "version": "7.7.9", "author": "Philipe Navarro @RasPhilCo", "bugs": "https://github.com/heroku/heroku-cli-autocomplete/issues", "dependencies": { diff --git a/packages/ci-v5/CHANGELOG.md b/packages/ci-v5/CHANGELOG.md index 62f0dc4735..c337f4e4fd 100644 --- a/packages/ci-v5/CHANGELOG.md +++ b/packages/ci-v5/CHANGELOG.md @@ -3,6 +3,15 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +## [7.7.9](https://github.com/heroku/cli/compare/v7.7.8...v7.7.9) (2018-08-14) + +**Note:** Version bump only for package @heroku-cli/plugin-ci-v5 + + + + + ## [7.5.10](https://github.com/heroku/cli/compare/v7.5.9...v7.5.10) (2018-07-03) diff --git a/packages/ci-v5/package.json b/packages/ci-v5/package.json index be250affb4..d4db4e3f14 100644 --- a/packages/ci-v5/package.json +++ b/packages/ci-v5/package.json @@ -1,7 +1,7 @@ { "name": "@heroku-cli/plugin-ci-v5", "description": "Heroku CLI plugin for Heroku CI", - "version": "7.5.10", + "version": "7.7.9", "author": "Andrew Appleton, Gudmundur Bjarni Olafsson, Max Beizer, Ransom Briggs", "bugs": "https://github.com/heroku/cli/issues", "cli-engine": { diff --git a/packages/ci/CHANGELOG.md b/packages/ci/CHANGELOG.md new file mode 100644 index 0000000000..381c5338d0 --- /dev/null +++ b/packages/ci/CHANGELOG.md @@ -0,0 +1,9 @@ +# Change Log + +All notable changes to this project will be documented in this file. +See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + + +## [7.7.9](https://github.com/heroku/cli/compare/v7.7.8...v7.7.9) (2018-08-14) + +**Note:** Version bump only for package @heroku-cli/plugin-ci diff --git a/packages/ci/README.md b/packages/ci/README.md index f3a830e0a0..82c9d42290 100644 --- a/packages/ci/README.md +++ b/packages/ci/README.md @@ -14,10 +14,104 @@ Heroku CLI plugin for Heroku CI [![License](https://img.shields.io/npm/l/@heroku-cli/plugin-ci.svg)](https://github.com/heroku/cli/blob/master/package.json) +* [Usage](#usage) +* [Commands](#commands) + # Usage +```sh-session +$ npm install -g @heroku-cli/plugin-ci +$ heroku COMMAND +running command... +$ heroku (-v|--version|version) +@heroku-cli/plugin-ci/7.7.9 darwin-x64 node-v8.11.0 +$ heroku --help [COMMAND] +USAGE + $ heroku COMMAND +... +``` + # Commands +* [`heroku ci:info TEST-RUN`](#heroku-ciinfo-test-run) +* [`heroku ci:last`](#heroku-cilast) +* [`heroku ci:rerun [NUMBER]`](#heroku-cirerun-number) +* [`heroku ci:run`](#heroku-cirun) + +## `heroku ci:info TEST-RUN` + +show the status of a specific test run + +``` +USAGE + $ heroku ci:info TEST-RUN + +OPTIONS + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline + --node=node the node number to show its setup and output + +EXAMPLE + $ heroku ci:info 1288 --app murmuring-headland-14719 +``` + +_See code: [src/commands/ci/info.ts](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/info.ts)_ + +## `heroku ci:last` + +looks for the most recent run and returns the output of that run + +``` +USAGE + $ heroku ci:last + +OPTIONS + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline + --node=node the node number to show its setup and output + +EXAMPLE + $ heroku ci:last --app murmuring-headland-14719 --node 100 +``` + +_See code: [src/commands/ci/last.ts](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/last.ts)_ + +## `heroku ci:rerun [NUMBER]` + +rerun tests against current directory + +``` +USAGE + $ heroku ci:rerun [NUMBER] + +OPTIONS + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline + +EXAMPLE + $ heroku ci:rerun 985 --app murmuring-headland-14719 +``` + +_See code: [src/commands/ci/rerun.ts](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/rerun.ts)_ + +## `heroku ci:run` + +run tests against current directory + +``` +USAGE + $ heroku ci:run + +OPTIONS + -a, --app=app app to run command against + -p, --pipeline=pipeline name of pipeline + +EXAMPLE + $ heroku ci:run --app murmuring-headland-14719 +``` + +_See code: [src/commands/ci/run.ts](https://github.com/heroku/cli/blob/v7.7.9/src/commands/ci/run.ts)_ + * [`heroku ci:info`](#heroku-ci-info) * [`heroku ci:last`](#heroku-ci-last) * [`heroku ci:run`](#heroku-ci-run) @@ -57,4 +151,4 @@ Re-run a previous test run. If no test run number is provided, the most recent t ``` USAGE $ heroku ci:rerun 555 --pipeline=my-pipeline # 555 is the test number -``` \ No newline at end of file +``` diff --git a/packages/ci/package.json b/packages/ci/package.json index 00afbf433d..e8e366ed04 100644 --- a/packages/ci/package.json +++ b/packages/ci/package.json @@ -1,7 +1,7 @@ { "name": "@heroku-cli/plugin-ci", "description": "Heroku CLI plugin for Heroku CI", - "version": "0.0.0", + "version": "7.7.9", "author": "Raúl Barroso @raulb", "bugs": "https://github.com/heroku/cli/issues", "dependencies": { diff --git a/packages/cli/CHANGELOG.md b/packages/cli/CHANGELOG.md index 4d3ec7a911..c3e4fa0b9f 100644 --- a/packages/cli/CHANGELOG.md +++ b/packages/cli/CHANGELOG.md @@ -3,6 +3,15 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +## [7.7.9](https://github.com/heroku/cli/compare/v7.7.8...v7.7.9) (2018-08-14) + +**Note:** Version bump only for package heroku + + + + + ## [7.7.8](https://github.com/heroku/cli/compare/v7.7.7...v7.7.8) (2018-07-30) diff --git a/packages/cli/package.json b/packages/cli/package.json index 067d49f19a..f521a9bac9 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -1,7 +1,7 @@ { "name": "heroku", "description": "CLI to interact with Heroku", - "version": "7.7.8", + "version": "7.7.9", "author": "Jeff Dickey @jdxcode", "bin": { "heroku": "./bin/run" @@ -12,12 +12,12 @@ "@heroku-cli/command": "8.1.26", "@heroku-cli/plugin-addons-v5": "^7.5.6", "@heroku-cli/plugin-apps-v5": "^7.7.8", - "@heroku-cli/plugin-auth": "^7.5.9", - "@heroku-cli/plugin-autocomplete": "^7.7.4", + "@heroku-cli/plugin-auth": "^7.7.9", + "@heroku-cli/plugin-autocomplete": "^7.7.9", "@heroku-cli/plugin-certs": "^7.5.9", "@heroku-cli/plugin-certs-v5": "^7.5.6", - "@heroku-cli/plugin-ci": "^0.0.0", - "@heroku-cli/plugin-ci-v5": "^7.5.10", + "@heroku-cli/plugin-ci": "^7.7.9", + "@heroku-cli/plugin-ci-v5": "^7.7.9", "@heroku-cli/plugin-config": "^7.5.9", "@heroku-cli/plugin-container-registry-v5": "^7.5.6", "@heroku-cli/plugin-git": "^7.5.9", @@ -30,7 +30,7 @@ "@heroku-cli/plugin-ps-exec": "2.3.4", "@heroku-cli/plugin-redis-v5": "^7.5.6", "@heroku-cli/plugin-run-v5": "^7.5.6", - "@heroku-cli/plugin-spaces": "^7.7.8", + "@heroku-cli/plugin-spaces": "^7.7.9", "@heroku-cli/plugin-status": "^7.5.9", "@heroku-cli/plugin-webhooks-v5": "^7.5.6", "@oclif/command": "1.4.34", diff --git a/packages/spaces/CHANGELOG.md b/packages/spaces/CHANGELOG.md index 2721bde776..7a7cc3e40f 100644 --- a/packages/spaces/CHANGELOG.md +++ b/packages/spaces/CHANGELOG.md @@ -3,6 +3,15 @@ All notable changes to this project will be documented in this file. See [Conventional Commits](https://conventionalcommits.org) for commit guidelines. + +## [7.7.9](https://github.com/heroku/cli/compare/v7.7.8...v7.7.9) (2018-08-14) + +**Note:** Version bump only for package @heroku-cli/plugin-spaces + + + + + ## [7.7.8](https://github.com/heroku/cli/compare/v7.7.7...v7.7.8) (2018-07-30) diff --git a/packages/spaces/README.md b/packages/spaces/README.md index 0da304e509..713b7257a3 100644 --- a/packages/spaces/README.md +++ b/packages/spaces/README.md @@ -18,6 +18,7 @@ heroku-spaces CLI plugin [![Circle CI](https://circleci.com/gh/heroku/heroku-spa * [`heroku spaces:ps`](#heroku-spacesps) * [`heroku spaces:rename`](#heroku-spacesrename) * [`heroku spaces:topology`](#heroku-spacestopology) +* [`heroku spaces:vpn:config`](#heroku-spacesvpnconfig) * [`heroku spaces:vpn:connect`](#heroku-spacesvpnconnect) * [`heroku spaces:vpn:connections`](#heroku-spacesvpnconnections) * [`heroku spaces:vpn:destroy`](#heroku-spacesvpndestroy) @@ -319,6 +320,37 @@ OPTIONS --json output in json format ``` +## `heroku spaces:vpn:config` + +display the configuration information for VPN + +``` +USAGE + $ heroku spaces:vpn:config + +OPTIONS + -n, --name=name name or id of the VPN connection to retrieve config from + -s, --space=space space the VPN connection belongs to + --json output in json format + +DESCRIPTION + Example: + + $ heroku spaces:vpn:config --space my-space vpn-connection-name + === vpn-connection-name VPN Tunnels + VPN Tunnel Customer Gateway VPN Gateway Pre-shared Key Routable Subnets IKE Version + ────────── ──────────────── ────────────── ────────────── ──────────────── ─────────── + Tunnel 1 104.196.121.200 35.171.237.136 abcdef12345 10.0.0.0/16 1 + Tunnel 2 104.196.121.200 52.44.7.216 fedcba54321 10.0.0.0/16 1 + + You will use the information provided by this command to establish a Private Space VPN Connection. + + - You must configure your VPN Gateway to use both Tunnels provided by Heroku + - The VPN Gateway values are the IP addresses of the Private Space Tunnels + - The Customer Gateway value is the Public IP of your VPN Gateway + - The VPN Gateway must use the IKE Version shown and the Pre-shared Keys as the authentication method +``` + ## `heroku spaces:vpn:connect` create VPN diff --git a/packages/spaces/package.json b/packages/spaces/package.json index 55e50bb3f9..ec41010f22 100644 --- a/packages/spaces/package.json +++ b/packages/spaces/package.json @@ -1,7 +1,7 @@ { "name": "@heroku-cli/plugin-spaces", "description": "Heroku plugin to manage Heroku Private Spaces", - "version": "7.7.8", + "version": "7.7.9", "author": "Heroku", "bugs": "https://github.com/heroku/cli/issues", "cli-engine": {