mirror of
https://github.com/balena-io/balena-cli.git
synced 2025-02-06 19:19:56 +00:00
commit
b74979fb9e
@ -115,9 +115,9 @@ The content sources for the auto generation of `docs/balena-cli.md` are:
|
|||||||
* [Selected
|
* [Selected
|
||||||
sections](https://github.com/balena-io/balena-cli/blob/v12.23.0/automation/capitanodoc/capitanodoc.ts#L199-L204)
|
sections](https://github.com/balena-io/balena-cli/blob/v12.23.0/automation/capitanodoc/capitanodoc.ts#L199-L204)
|
||||||
of the README file.
|
of the README file.
|
||||||
* The CLI's command documentation in source code (`lib/commands/` folder), for example:
|
* The CLI's command documentation in source code (`src/commands/` folder), for example:
|
||||||
* `lib/commands/push.ts`
|
* `src/commands/push.ts`
|
||||||
* `lib/commands/env/add.ts`
|
* `src/commands/env/add.ts`
|
||||||
|
|
||||||
The README file is manually edited, but subsections are automatically extracted for inclusion in
|
The README file is manually edited, but subsections are automatically extracted for inclusion in
|
||||||
`docs/balena-cli.md` by the `getCapitanoDoc()` function in
|
`docs/balena-cli.md` by the `getCapitanoDoc()` function in
|
||||||
@ -224,7 +224,7 @@ command, or by manually editing or copying files to the `node_modules` folder.
|
|||||||
|
|
||||||
Unexpected behavior may then be observed because of the CLI's use of the
|
Unexpected behavior may then be observed because of the CLI's use of the
|
||||||
[fast-boot2](https://www.npmjs.com/package/fast-boot2) package that caches module resolution.
|
[fast-boot2](https://www.npmjs.com/package/fast-boot2) package that caches module resolution.
|
||||||
`fast-boot2` is configured in `lib/fast-boot.ts` to automatically invalidate the cache if
|
`fast-boot2` is configured in `src/fast-boot.ts` to automatically invalidate the cache if
|
||||||
changes are made to the `package.json` or `npm-shrinkwrap.json` files, but the cache won't
|
changes are made to the `package.json` or `npm-shrinkwrap.json` files, but the cache won't
|
||||||
be automatically invalidated if `npm link` is used or if manual modifications are made to the
|
be automatically invalidated if `npm link` is used or if manual modifications are made to the
|
||||||
`node_modules` folder. In this situation:
|
`node_modules` folder. In this situation:
|
||||||
|
@ -40,7 +40,7 @@ By default, the CLI is installed to the following folders:
|
|||||||
OS | Folders
|
OS | Folders
|
||||||
--- | ---
|
--- | ---
|
||||||
Windows: | `C:\Program Files\balena-cli\`
|
Windows: | `C:\Program Files\balena-cli\`
|
||||||
macOS: | `/usr/local/lib/balena-cli/` <br> `/usr/local/bin/balena`
|
macOS: | `/usr/local/src/balena-cli/` <br> `/usr/local/bin/balena`
|
||||||
|
|
||||||
## Standalone Zip Package
|
## Standalone Zip Package
|
||||||
|
|
||||||
|
@ -27,7 +27,7 @@ To update the balena CLI, repeat the steps above for the new version.
|
|||||||
To uninstall it, run the following command on a terminal prompt:
|
To uninstall it, run the following command on a terminal prompt:
|
||||||
|
|
||||||
```text
|
```text
|
||||||
sudo /usr/local/lib/balena-cli/bin/uninstall
|
sudo /usr/local/src/balena-cli/bin/uninstall
|
||||||
```
|
```
|
||||||
|
|
||||||
## Additional Dependencies
|
## Additional Dependencies
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import type { JsonVersions } from '../lib/commands/version/index';
|
import type { JsonVersions } from '../src/commands/version/index';
|
||||||
|
|
||||||
import { run as oclifRun } from '@oclif/core';
|
import { run as oclifRun } from '@oclif/core';
|
||||||
import * as archiver from 'archiver';
|
import * as archiver from 'archiver';
|
||||||
|
@ -28,7 +28,7 @@ import { GlobSync } from 'glob';
|
|||||||
*
|
*
|
||||||
* IMPORTANT
|
* IMPORTANT
|
||||||
*
|
*
|
||||||
* All commands need to be stored under a folder in lib/commands to maintain uniformity
|
* All commands need to be stored under a folder in src/commands to maintain uniformity
|
||||||
* Generating docs will error out if directive not followed
|
* Generating docs will error out if directive not followed
|
||||||
* To add a custom heading for command docs, add the heading next to the folder name
|
* To add a custom heading for command docs, add the heading next to the folder name
|
||||||
* in the `commandHeadings` dictionary.
|
* in the `commandHeadings` dictionary.
|
||||||
|
@ -18,7 +18,7 @@ import * as path from 'path';
|
|||||||
import { getCapitanoDoc } from './capitanodoc';
|
import { getCapitanoDoc } from './capitanodoc';
|
||||||
import type { Category, Document, OclifCommand } from './doc-types';
|
import type { Category, Document, OclifCommand } from './doc-types';
|
||||||
import * as markdown from './markdown';
|
import * as markdown from './markdown';
|
||||||
import { stripIndent } from '../../lib/utils/lazy';
|
import { stripIndent } from '../../src/utils/lazy';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Generates the markdown document (as a string) for the CLI documentation
|
* Generates the markdown document (as a string) for the CLI documentation
|
||||||
|
@ -18,8 +18,8 @@ import { Parser } from '@oclif/core';
|
|||||||
import * as ent from 'ent';
|
import * as ent from 'ent';
|
||||||
import * as _ from 'lodash';
|
import * as _ from 'lodash';
|
||||||
|
|
||||||
import { getManualSortCompareFunction } from '../../lib/utils/helpers';
|
import { getManualSortCompareFunction } from '../../src/utils/helpers';
|
||||||
import { capitanoizeOclifUsage } from '../../lib/utils/oclif-utils';
|
import { capitanoizeOclifUsage } from '../../src/utils/oclif-utils';
|
||||||
import type { Category, Document, OclifCommand } from './doc-types';
|
import type { Category, Document, OclifCommand } from './doc-types';
|
||||||
|
|
||||||
function renderOclifCommand(command: OclifCommand): string[] {
|
function renderOclifCommand(command: OclifCommand): string[] {
|
||||||
|
@ -43,8 +43,8 @@ async function checkBuildTimestamps() {
|
|||||||
...gitStatus.staged,
|
...gitStatus.staged,
|
||||||
...gitStatus.renamed.map((o) => o.to),
|
...gitStatus.renamed.map((o) => o.to),
|
||||||
])
|
])
|
||||||
// select only staged files that start with lib/ or typings/
|
// select only staged files that start with src/ or typings/
|
||||||
.filter((f) => f.match(/^(lib|typings)[/\\]/))
|
.filter((f) => f.match(/^(src|typings)[/\\]/))
|
||||||
.map((f) => path.join(ROOT, f));
|
.map((f) => path.join(ROOT, f));
|
||||||
|
|
||||||
const fStats = await Promise.all(stagedFiles.map((f) => fs.stat(f)));
|
const fStats = await Promise.all(stagedFiles.map((f) => fs.stat(f)));
|
||||||
|
10
bin/dev.js
10
bin/dev.js
@ -29,7 +29,7 @@ const path = require('path');
|
|||||||
const rootDir = path.join(__dirname, '..');
|
const rootDir = path.join(__dirname, '..');
|
||||||
|
|
||||||
// Allow balena-dev to work with oclif by temporarily
|
// Allow balena-dev to work with oclif by temporarily
|
||||||
// pointing oclif config options to lib/ instead of build/
|
// pointing oclif config options to src/ instead of build/
|
||||||
modifyOclifPaths();
|
modifyOclifPaths();
|
||||||
// Undo changes on exit
|
// Undo changes on exit
|
||||||
process.on('exit', function () {
|
process.on('exit', function () {
|
||||||
@ -57,9 +57,9 @@ require('ts-node').register({
|
|||||||
project: path.join(rootDir, 'tsconfig.json'),
|
project: path.join(rootDir, 'tsconfig.json'),
|
||||||
transpileOnly: true,
|
transpileOnly: true,
|
||||||
});
|
});
|
||||||
require('../lib/app').run(undefined, { dir: __dirname, development: true });
|
require('../src/app').run(undefined, { dir: __dirname, development: true });
|
||||||
|
|
||||||
// Modify package.json oclif paths from build/ -> lib/, or vice versa
|
// Modify package.json oclif paths from build/ -> src/, or vice versa
|
||||||
function modifyOclifPaths(revert) {
|
function modifyOclifPaths(revert) {
|
||||||
const fs = require('fs');
|
const fs = require('fs');
|
||||||
const packageJsonPath = path.join(rootDir, 'package.json');
|
const packageJsonPath = path.join(rootDir, 'package.json');
|
||||||
@ -73,9 +73,9 @@ function modifyOclifPaths(revert) {
|
|||||||
|
|
||||||
let oclifSectionText = JSON.stringify(packageObj.oclif);
|
let oclifSectionText = JSON.stringify(packageObj.oclif);
|
||||||
if (!revert) {
|
if (!revert) {
|
||||||
oclifSectionText = oclifSectionText.replace(/\/build\//g, '/lib/');
|
oclifSectionText = oclifSectionText.replace(/\/build\//g, '/src/');
|
||||||
} else {
|
} else {
|
||||||
oclifSectionText = oclifSectionText.replace(/\/lib\//g, '/build/');
|
oclifSectionText = oclifSectionText.replace(/\/src\//g, '/build/');
|
||||||
}
|
}
|
||||||
|
|
||||||
packageObj.oclif = JSON.parse(oclifSectionText);
|
packageObj.oclif = JSON.parse(oclifSectionText);
|
||||||
|
@ -2168,13 +2168,9 @@ fleet name or slug (preferred)
|
|||||||
|
|
||||||
open fleet dashboard page
|
open fleet dashboard page
|
||||||
|
|
||||||
#### --fields FIELDS
|
|
||||||
|
|
||||||
only show provided fields (comma-separated)
|
|
||||||
|
|
||||||
#### -j, --json
|
#### -j, --json
|
||||||
|
|
||||||
output in json format
|
produce JSON output instead of tabular output
|
||||||
|
|
||||||
## fleet pin <slug> [releaseToPinTo]
|
## fleet pin <slug> [releaseToPinTo]
|
||||||
|
|
||||||
@ -2353,29 +2349,9 @@ Examples:
|
|||||||
|
|
||||||
### Options
|
### Options
|
||||||
|
|
||||||
#### --fields FIELDS
|
|
||||||
|
|
||||||
only show provided fields (comma-separated)
|
|
||||||
|
|
||||||
#### -j, --json
|
#### -j, --json
|
||||||
|
|
||||||
output in json format
|
produce JSON output instead of tabular output
|
||||||
|
|
||||||
#### --filter FILTER
|
|
||||||
|
|
||||||
filter results by substring matching of a given field, eg: --filter field=foo
|
|
||||||
|
|
||||||
#### --no-header
|
|
||||||
|
|
||||||
hide table header from output
|
|
||||||
|
|
||||||
#### --no-truncate
|
|
||||||
|
|
||||||
do not truncate output to fit screen
|
|
||||||
|
|
||||||
#### --sort SORT
|
|
||||||
|
|
||||||
field to sort by (prepend '-' for descending order)
|
|
||||||
|
|
||||||
# Local
|
# Local
|
||||||
|
|
||||||
|
@ -1,19 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright 2020 Balena
|
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
you may not use this file except in compliance with the License.
|
|
||||||
You may obtain a copy of the License at
|
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
|
|
||||||
Unless required by applicable law or agreed to in writing, software
|
|
||||||
distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
See the License for the specific language governing permissions and
|
|
||||||
limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
import type { DataOutputOptions, DataSetOutputOptions } from './output';
|
|
||||||
|
|
||||||
export { DataOutputOptions, DataSetOutputOptions };
|
|
@ -1,158 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright 2020 Balena
|
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
you may not use this file except in compliance with the License.
|
|
||||||
You may obtain a copy of the License at
|
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
|
|
||||||
Unless required by applicable law or agreed to in writing, software
|
|
||||||
distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
See the License for the specific language governing permissions and
|
|
||||||
limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
import { getCliUx, getChalk } from '../utils/lazy';
|
|
||||||
|
|
||||||
export interface DataOutputOptions {
|
|
||||||
fields?: string;
|
|
||||||
json?: boolean;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface DataSetOutputOptions extends DataOutputOptions {
|
|
||||||
filter?: string;
|
|
||||||
'no-header'?: boolean;
|
|
||||||
'no-truncate'?: boolean;
|
|
||||||
sort?: string;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Output message to STDERR
|
|
||||||
*/
|
|
||||||
export function outputMessage(msg: string) {
|
|
||||||
// Messages go to STDERR
|
|
||||||
console.error(msg);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Output result data to STDOUT
|
|
||||||
* Supports:
|
|
||||||
* - arrays of items (displayed in a tabular way),
|
|
||||||
* - single items (displayed in a field per row format).
|
|
||||||
*
|
|
||||||
* @param data Array of data objects to output
|
|
||||||
* @param fields Array of fieldnames, specifying the fields and display order
|
|
||||||
* @param options Output options
|
|
||||||
*/
|
|
||||||
export async function outputData(
|
|
||||||
data: any[] | object,
|
|
||||||
fields: string[],
|
|
||||||
options: DataOutputOptions | DataSetOutputOptions,
|
|
||||||
) {
|
|
||||||
if (Array.isArray(data)) {
|
|
||||||
await outputDataSet(data, fields, options as DataSetOutputOptions);
|
|
||||||
} else {
|
|
||||||
await outputDataItem(data, fields, options as DataOutputOptions);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Wraps the cli.ux table implementation, to output tabular data
|
|
||||||
*
|
|
||||||
* @param data Array of data objects to output
|
|
||||||
* @param fields Array of fieldnames, specifying the fields and display order
|
|
||||||
* @param options Output options
|
|
||||||
*/
|
|
||||||
async function outputDataSet(
|
|
||||||
data: any[],
|
|
||||||
fields: string[],
|
|
||||||
options: DataSetOutputOptions,
|
|
||||||
) {
|
|
||||||
// Oclif expects fields to be specified in the format used in table headers (though lowercase)
|
|
||||||
// By replacing underscores with spaces here, we can support both header format and actual field name
|
|
||||||
// (e.g. as seen in json output).
|
|
||||||
options.fields = options.fields?.replace(/_/g, ' ');
|
|
||||||
options.filter = options.filter?.replace(/_/g, ' ');
|
|
||||||
options.sort = options.sort?.replace(/_/g, ' ');
|
|
||||||
|
|
||||||
getCliUx().table(
|
|
||||||
data,
|
|
||||||
// Convert fields array to column object keys
|
|
||||||
// that cli.ux expects. We can later add support
|
|
||||||
// for both formats if beneficial
|
|
||||||
fields.reduce((ac, a) => ({ ...ac, [a]: {} }), {}),
|
|
||||||
{
|
|
||||||
...options,
|
|
||||||
...(options.json
|
|
||||||
? {
|
|
||||||
output: 'json',
|
|
||||||
}
|
|
||||||
: {}),
|
|
||||||
columns: options.fields,
|
|
||||||
printLine,
|
|
||||||
},
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Outputs a single data object (like `resin-cli-visuals table.vertical`),
|
|
||||||
* but supporting a subset of options from `cli-ux table` (--json and --fields)
|
|
||||||
*
|
|
||||||
* @param data Array of data objects to output
|
|
||||||
* @param fields Array of fieldnames, specifying the fields and display order
|
|
||||||
* @param options Output options
|
|
||||||
*/
|
|
||||||
async function outputDataItem(
|
|
||||||
data: any,
|
|
||||||
fields: string[],
|
|
||||||
options: DataOutputOptions,
|
|
||||||
) {
|
|
||||||
const outData: typeof data = {};
|
|
||||||
|
|
||||||
// Convert comma separated list of fields in `options.fields` to array of correct format.
|
|
||||||
// Note, user may have specified the true field name (e.g. `some_field`),
|
|
||||||
// or the format displayed in headers (e.g. `Some field`, case insensitive).
|
|
||||||
const userSelectedFields = options.fields?.split(',').map((f) => {
|
|
||||||
return f.toLowerCase().trim().replace(/ /g, '_');
|
|
||||||
});
|
|
||||||
|
|
||||||
// Order and filter the fields based on `fields` parameter and `options.fields`
|
|
||||||
(userSelectedFields || fields).forEach((fieldName) => {
|
|
||||||
if (fields.includes(fieldName)) {
|
|
||||||
outData[fieldName] = data[fieldName];
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
if (options.json) {
|
|
||||||
printLine(JSON.stringify(outData, undefined, 2));
|
|
||||||
} else {
|
|
||||||
const chalk = getChalk();
|
|
||||||
const { capitalize } = await import('lodash');
|
|
||||||
|
|
||||||
// Find longest key, so we can align results
|
|
||||||
const longestKeyLength = getLongestObjectKeyLength(outData);
|
|
||||||
|
|
||||||
// Output one field per line
|
|
||||||
for (const [k, v] of Object.entries(outData)) {
|
|
||||||
const shim = ' '.repeat(longestKeyLength - k.length);
|
|
||||||
const kDisplay = capitalize(k.replace(/_/g, ' '));
|
|
||||||
printLine(`${chalk.bold(kDisplay) + shim} : ${v}`);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function getLongestObjectKeyLength(o: any): number {
|
|
||||||
return Object.keys(o).length >= 1
|
|
||||||
? Object.keys(o).reduce((a, b) => {
|
|
||||||
return a.length > b.length ? a : b;
|
|
||||||
}).length
|
|
||||||
: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
function printLine(s: any) {
|
|
||||||
// Duplicating oclif cli-ux's default implementation here,
|
|
||||||
// but using this one explicitly for ease of testing
|
|
||||||
process.stdout.write(s + '\n');
|
|
||||||
}
|
|
749
npm-shrinkwrap.json
generated
749
npm-shrinkwrap.json
generated
File diff suppressed because it is too large
Load Diff
@ -14,7 +14,7 @@
|
|||||||
"bin/",
|
"bin/",
|
||||||
"build/",
|
"build/",
|
||||||
"doc/",
|
"doc/",
|
||||||
"lib/",
|
"src/",
|
||||||
"patches/",
|
"patches/",
|
||||||
"!patches/**/**.dev.patch",
|
"!patches/**/**.dev.patch",
|
||||||
"*.md",
|
"*.md",
|
||||||
@ -51,7 +51,7 @@
|
|||||||
"build": "npm run build:src && npm run catch-uncommitted",
|
"build": "npm run build:src && npm run catch-uncommitted",
|
||||||
"build:t": "npm run lint && npm run build:fast && npm run build:test",
|
"build:t": "npm run lint && npm run build:fast && npm run build:test",
|
||||||
"build:src": "npm run lint && npm run build:fast && npm run build:test && npm run build:doc && npm run build:completion",
|
"build:src": "npm run lint && npm run build:fast && npm run build:test && npm run build:doc && npm run build:completion",
|
||||||
"build:pages": "mkdirp ./build/auth/pages/&& inline-source --compress ./lib/auth/pages/error.ejs ./build/auth/pages/error.ejs && inline-source --compress ./lib/auth/pages/success.ejs ./build/auth/pages/success.ejs",
|
"build:pages": "mkdirp ./build/auth/pages/&& inline-source --compress ./src/auth/pages/error.ejs ./build/auth/pages/error.ejs && inline-source --compress ./src/auth/pages/success.ejs ./build/auth/pages/success.ejs",
|
||||||
"build:fast": "npm run build:pages && tsc && npx oclif manifest",
|
"build:fast": "npm run build:pages && tsc && npx oclif manifest",
|
||||||
"build:test": "tsc -P ./tsconfig.dev.json --noEmit",
|
"build:test": "tsc -P ./tsconfig.dev.json --noEmit",
|
||||||
"build:doc": "ts-node --transpile-only automation/capitanodoc/index.ts > docs/balena-cli.md",
|
"build:doc": "ts-node --transpile-only automation/capitanodoc/index.ts > docs/balena-cli.md",
|
||||||
@ -73,7 +73,7 @@
|
|||||||
"catch-uncommitted": "ts-node --transpile-only automation/run.ts catch-uncommitted",
|
"catch-uncommitted": "ts-node --transpile-only automation/run.ts catch-uncommitted",
|
||||||
"ci": "npm run test && npm run catch-uncommitted",
|
"ci": "npm run test && npm run catch-uncommitted",
|
||||||
"lint": "npm run lint-tsconfig && npm run lint-other",
|
"lint": "npm run lint-tsconfig && npm run lint-other",
|
||||||
"lint-tsconfig": "balena-lint -e ts -e js -t tsconfig.dev.json --fix automation/ lib/ tests/ typings/",
|
"lint-tsconfig": "balena-lint -e ts -e js -t tsconfig.dev.json --fix automation/ src/ tests/ typings/",
|
||||||
"lint-other": "balena-lint -e ts -e js --fix bin/run.js bin/dev.js completion/ .mocharc.js .mocharc-standalone.js",
|
"lint-other": "balena-lint -e ts -e js --fix bin/run.js bin/dev.js completion/ .mocharc.js .mocharc-standalone.js",
|
||||||
"update": "ts-node --transpile-only ./automation/update-module.ts",
|
"update": "ts-node --transpile-only ./automation/update-module.ts",
|
||||||
"prepare": "echo {} > bin/.fast-boot.json",
|
"prepare": "echo {} > bin/.fast-boot.json",
|
||||||
@ -199,7 +199,7 @@
|
|||||||
"typescript": "^5.5.2"
|
"typescript": "^5.5.2"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@balena/compose": "^3.2.1",
|
"@balena/compose": "^4.0.1",
|
||||||
"@balena/dockerignore": "^1.0.2",
|
"@balena/dockerignore": "^1.0.2",
|
||||||
"@balena/env-parsing": "^1.1.8",
|
"@balena/env-parsing": "^1.1.8",
|
||||||
"@balena/es-version": "^1.0.1",
|
"@balena/es-version": "^1.0.1",
|
||||||
|
Before Width: | Height: | Size: 2.3 KiB After Width: | Height: | Size: 2.3 KiB |
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 2.6 KiB |
@ -21,7 +21,6 @@ import {
|
|||||||
NotAvailableInOfflineModeError,
|
NotAvailableInOfflineModeError,
|
||||||
} from './errors';
|
} from './errors';
|
||||||
import { stripIndent } from './utils/lazy';
|
import { stripIndent } from './utils/lazy';
|
||||||
import * as output from './framework/output';
|
|
||||||
|
|
||||||
export default abstract class BalenaCommand extends Command {
|
export default abstract class BalenaCommand extends Command {
|
||||||
/**
|
/**
|
||||||
@ -168,7 +167,4 @@ export default abstract class BalenaCommand extends Command {
|
|||||||
await this.getStdin();
|
await this.getStdin();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected outputMessage = output.outputMessage;
|
|
||||||
protected outputData = output.outputData;
|
|
||||||
}
|
}
|
@ -20,7 +20,7 @@ import { Flags } from '@oclif/core';
|
|||||||
import Command from '../../command';
|
import Command from '../../command';
|
||||||
import * as cf from '../../utils/common-flags';
|
import * as cf from '../../utils/common-flags';
|
||||||
import * as ca from '../../utils/common-args';
|
import * as ca from '../../utils/common-args';
|
||||||
import { getBalenaSdk, stripIndent } from '../../utils/lazy';
|
import { getBalenaSdk, getVisuals, stripIndent } from '../../utils/lazy';
|
||||||
import { applicationIdInfo } from '../../utils/messages';
|
import { applicationIdInfo } from '../../utils/messages';
|
||||||
|
|
||||||
export default class FleetCmd extends Command {
|
export default class FleetCmd extends Command {
|
||||||
@ -49,7 +49,7 @@ export default class FleetCmd extends Command {
|
|||||||
default: false,
|
default: false,
|
||||||
description: 'open fleet dashboard page',
|
description: 'open fleet dashboard page',
|
||||||
}),
|
}),
|
||||||
...cf.dataOutputFlags,
|
json: cf.json,
|
||||||
};
|
};
|
||||||
|
|
||||||
public static authenticated = true;
|
public static authenticated = true;
|
||||||
@ -78,16 +78,28 @@ export default class FleetCmd extends Command {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const outputApplication = {
|
const applicationToDisplay = {
|
||||||
...application,
|
id: application.id,
|
||||||
|
app_name: application.app_name,
|
||||||
|
slug: application.slug,
|
||||||
device_type: application.is_for__device_type[0].slug,
|
device_type: application.is_for__device_type[0].slug,
|
||||||
commit: application.should_be_running__release[0]?.commit,
|
commit: application.should_be_running__release[0]?.commit,
|
||||||
};
|
};
|
||||||
|
|
||||||
await this.outputData(
|
if (options.json) {
|
||||||
outputApplication,
|
console.log(JSON.stringify(applicationToDisplay, null, 4));
|
||||||
['app_name', 'id', 'device_type', 'slug', 'commit'],
|
return;
|
||||||
options,
|
}
|
||||||
|
|
||||||
|
// Emulate table.vertical title output, but avoid uppercasing and inserting spaces
|
||||||
|
console.log(`== ${applicationToDisplay.app_name}`);
|
||||||
|
console.log(
|
||||||
|
getVisuals().table.vertical(applicationToDisplay, [
|
||||||
|
'id',
|
||||||
|
'device_type',
|
||||||
|
'slug',
|
||||||
|
'commit',
|
||||||
|
]),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -19,7 +19,7 @@ import type * as BalenaSdk from 'balena-sdk';
|
|||||||
|
|
||||||
import Command from '../../command';
|
import Command from '../../command';
|
||||||
import * as cf from '../../utils/common-flags';
|
import * as cf from '../../utils/common-flags';
|
||||||
import { getBalenaSdk, stripIndent } from '../../utils/lazy';
|
import { getBalenaSdk, getVisuals, stripIndent } from '../../utils/lazy';
|
||||||
|
|
||||||
interface ExtendedApplication extends ApplicationWithDeviceTypeSlug {
|
interface ExtendedApplication extends ApplicationWithDeviceTypeSlug {
|
||||||
device_count: number;
|
device_count: number;
|
||||||
@ -42,8 +42,8 @@ export default class FleetsCmd extends Command {
|
|||||||
public static usage = 'fleets';
|
public static usage = 'fleets';
|
||||||
|
|
||||||
public static flags = {
|
public static flags = {
|
||||||
...cf.dataSetOutputFlags,
|
|
||||||
help: cf.help,
|
help: cf.help,
|
||||||
|
json: cf.json,
|
||||||
};
|
};
|
||||||
|
|
||||||
public static authenticated = true;
|
public static authenticated = true;
|
||||||
@ -77,17 +77,29 @@ export default class FleetsCmd extends Command {
|
|||||||
application.device_type = application.is_for__device_type[0].slug;
|
application.device_type = application.is_for__device_type[0].slug;
|
||||||
});
|
});
|
||||||
|
|
||||||
await this.outputData(
|
const applicationsToDisplay = applications.map((application) => ({
|
||||||
applications,
|
id: application.id,
|
||||||
[
|
app_name: application.app_name,
|
||||||
|
slug: application.slug,
|
||||||
|
device_type: application.device_type,
|
||||||
|
online_devices: application.online_devices,
|
||||||
|
device_count: application.device_count,
|
||||||
|
}));
|
||||||
|
|
||||||
|
if (options.json) {
|
||||||
|
console.log(JSON.stringify(applicationsToDisplay, null, 4));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log(
|
||||||
|
getVisuals().table.horizontal(applicationsToDisplay, [
|
||||||
'id',
|
'id',
|
||||||
'app_name',
|
'app_name => NAME',
|
||||||
'slug',
|
'slug',
|
||||||
'device_type',
|
'device_type',
|
||||||
'device_count',
|
'device_count',
|
||||||
'online_devices',
|
'online_devices',
|
||||||
],
|
]),
|
||||||
options,
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user