diff --git a/.changeset/warn-error-output-colon.md b/.changeset/warn-error-output-colon.md new file mode 100644 index 0000000000..ee03addcf7 --- /dev/null +++ b/.changeset/warn-error-output-colon.md @@ -0,0 +1,6 @@ +--- +"@pnpm/cli.default-reporter": patch +"pnpm": patch +--- + +The `WARN` and error code labels in pnpm's output now wrap in brackets (`[WARN]`, `[ERR_PNPM_FOO]`). Previously the labels relied entirely on a colored background to stand out, which meant they blended into the surrounding text in terminals without color (e.g. when `NO_COLOR` is set or output is piped). The brackets are painted in the same color as the badge background, so they appear as ordinary padding in color-capable terminals — only the no-color rendering changes. diff --git a/cli/default-reporter/src/reportError.ts b/cli/default-reporter/src/reportError.ts index 65bfe61dfa..53a791faa2 100644 --- a/cli/default-reporter/src/reportError.ts +++ b/cli/default-reporter/src/reportError.ts @@ -304,7 +304,7 @@ function formatGenericError (errorMessage: string, stack: object): ErrorInfo { } function formatErrorSummary (message: string, code?: string): string { - return `${chalk.bgRed.black(`\u2009${code ?? 'ERROR'}\u2009`)} ${chalk.red(message)}` + return `${chalk.bgRed.red('[')}${chalk.bgRed.black(code ?? 'ERROR')}${chalk.bgRed.red(']')} ${chalk.red(message)}` } function reportModifiedDependency (msg: { modified: string[] }): ErrorInfo { diff --git a/cli/default-reporter/src/reporterForClient/utils/formatWarn.ts b/cli/default-reporter/src/reporterForClient/utils/formatWarn.ts index 6ce6c1be35..4a50654b92 100644 --- a/cli/default-reporter/src/reporterForClient/utils/formatWarn.ts +++ b/cli/default-reporter/src/reporterForClient/utils/formatWarn.ts @@ -1,8 +1,5 @@ import chalk from 'chalk' export function formatWarn (message: string): string { - // The \u2009 is the "thin space" unicode character - // It is used instead of ' ' because chalk (as of version 2.1.0) - // trims whitespace at the beginning - return `${chalk.bgYellow.black('\u2009WARN\u2009')} ${message}` + return `${chalk.bgYellow.yellow('[')}${chalk.bgYellow.black('WARN')}${chalk.bgYellow.yellow(']')} ${message}` } diff --git a/cli/default-reporter/test/index.ts b/cli/default-reporter/test/index.ts index 7a8a40a3f1..d696daf9af 100644 --- a/cli/default-reporter/test/index.ts +++ b/cli/default-reporter/test/index.ts @@ -27,7 +27,7 @@ import { map, skip, take } from 'rxjs/operators' import { formatWarn } from '../src/reporterForClient/utils/formatWarn.js' -const formatErrorCode = (code: string) => chalk.bgRed.black(`\u2009${code}\u2009`) +const formatErrorCode = (code: string) => chalk.bgRed.red('[') + chalk.bgRed.black(code) + chalk.bgRed.red(']') const formatError = (code: string, message: string) => { return `${formatErrorCode(code)} ${chalk.red(message)}` } diff --git a/cli/default-reporter/test/reportingErrors.ts b/cli/default-reporter/test/reportingErrors.ts index 557d6e5c91..17fbe6ebc5 100644 --- a/cli/default-reporter/test/reportingErrors.ts +++ b/cli/default-reporter/test/reportingErrors.ts @@ -19,7 +19,7 @@ interface Exception extends NodeJS.ErrnoException { stage?: string } -const formatErrorCode = (code: string) => chalk.bgRed.black(`\u2009${code}\u2009`) +const formatErrorCode = (code: string) => chalk.bgRed.red('[') + chalk.bgRed.black(code) + chalk.bgRed.red(']') const formatError = (code: string, message: string) => { return `${formatErrorCode(code)} ${chalk.red(message)}` } diff --git a/pnpm/src/formatError.ts b/pnpm/src/formatError.ts index bb230e6e7d..d40a375cb5 100644 --- a/pnpm/src/formatError.ts +++ b/pnpm/src/formatError.ts @@ -1,7 +1,7 @@ import chalk from 'chalk' export function formatUnknownOptionsError (unknownOptions: Map): string { - let output = chalk.bgRed.black('\u2009ERROR\u2009') + let output = chalk.bgRed.red('[') + chalk.bgRed.black('ERROR') + chalk.bgRed.red(']') const unknownOptionsArray = Array.from(unknownOptions.keys()) if (unknownOptionsArray.length > 1) { return `${output} ${chalk.red(`Unknown options: ${unknownOptionsArray.map(unknownOption => `'${unknownOption}'`).join(', ')}`)}` diff --git a/pnpm/src/main.ts b/pnpm/src/main.ts index b26ca4e2bb..95ee1f9079 100644 --- a/pnpm/src/main.ts +++ b/pnpm/src/main.ts @@ -374,7 +374,7 @@ export async function main (inputArgv: string[]): Promise { } function printError (message: string, hint?: string): void { - const ERROR = chalk.bgRed.black('\u2009ERROR\u2009') + const ERROR = chalk.bgRed.red('[') + chalk.bgRed.black('ERROR') + chalk.bgRed.red(']') console.error(`${message.startsWith(ERROR) ? '' : ERROR + ' '}${chalk.red(message)}`) if (hint) { console.error(hint) diff --git a/pnpm/test/errorHandler.test.ts b/pnpm/test/errorHandler.test.ts index 587cdfb0f1..b0d44ba8f8 100644 --- a/pnpm/test/errorHandler.test.ts +++ b/pnpm/test/errorHandler.test.ts @@ -92,5 +92,5 @@ test('should print error summary when some packages fail with --no-bail', async const output = stdout.toString() expect(output).toContain('ERR_PNPM_RECURSIVE_FAIL') expect(output).toContain('Summary: 1 fails, 2 passes') - expect(output).toContain('ERROR  project-2@1.0.0 build: `exit 1`') + expect(output).toContain('[ERROR] project-2@1.0.0 build: `exit 1`') }) diff --git a/pnpm/test/formatError.test.ts b/pnpm/test/formatError.test.ts index 105990da3a..3b002b4fb1 100644 --- a/pnpm/test/formatError.test.ts +++ b/pnpm/test/formatError.test.ts @@ -8,17 +8,17 @@ test('formatUnknownOptionsError()', async () => { expect( stripAnsi(formatUnknownOptionsError(new Map([['foo', []]]))) ).toBe( - "\u2009ERROR\u2009 Unknown option: 'foo'" + "[ERROR] Unknown option: 'foo'" ) expect( stripAnsi(formatUnknownOptionsError(new Map([['foo', ['foa', 'fob']]]))) ).toBe( - `\u2009ERROR\u2009 Unknown option: 'foo' + `[ERROR] Unknown option: 'foo' Did you mean 'foa', or 'fob'? Use "--config.unknown=value" to force an unknown option.` ) expect( stripAnsi(formatUnknownOptionsError(new Map([['foo', []], ['bar', []]]))) ).toBe( - "\u2009ERROR\u2009 Unknown options: 'foo', 'bar'" + "[ERROR] Unknown options: 'foo', 'bar'" ) })