Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
c90765e10d | ||
|
|
ad2e1d76b7 | ||
|
|
65d344bae8 | ||
|
|
8a1dd7b324 |
+2
-2
@@ -17,9 +17,9 @@
|
||||
"dependencies": {
|
||||
"@semantic-release/commit-analyzer": "^3.0.1",
|
||||
"@semantic-release/condition-travis": "^6.0.0",
|
||||
"@semantic-release/error": "^2.0.0",
|
||||
"@semantic-release/error": "^2.1.0",
|
||||
"@semantic-release/last-release-npm": "^2.0.0",
|
||||
"@semantic-release/release-notes-generator": "^4.0.0",
|
||||
"@semantic-release/release-notes-generator": "^5.0.0",
|
||||
"chalk": "^2.3.0",
|
||||
"commander": "^2.11.0",
|
||||
"debug": "^3.1.0",
|
||||
|
||||
+2
-3
@@ -1,5 +1,4 @@
|
||||
const program = require('commander');
|
||||
const SemanticReleaseError = require('@semantic-release/error');
|
||||
const logger = require('./lib/logger');
|
||||
|
||||
function list(values) {
|
||||
@@ -49,11 +48,11 @@ module.exports = async () => {
|
||||
} catch (err) {
|
||||
// If error is a SemanticReleaseError then it's an expected exception case (no release to be done, running on a PR etc..) and the cli will return with 0
|
||||
// Otherwise it's an unexpected error (configuration issue, code issue, plugin issue etc...) and the cli will return 1
|
||||
if (err instanceof SemanticReleaseError) {
|
||||
if (err.semanticRelease) {
|
||||
logger.log(`%s ${err.message}`, err.code);
|
||||
} else {
|
||||
process.exitCode = 1;
|
||||
logger.error(err);
|
||||
logger.error('An error occurred while running semantic-release: %O', err);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
+8
-3
@@ -6,13 +6,18 @@ const chalk = require('chalk');
|
||||
module.exports = {
|
||||
log(...args) {
|
||||
const [format, ...rest] = args;
|
||||
console.log(`${chalk.grey('[Semantic release]:')} ${format}`, ...rest.map(arg => chalk.magenta(arg)));
|
||||
console.log(
|
||||
`${chalk.grey('[Semantic release]:')}${typeof format === 'string'
|
||||
? ` ${format.replace(/%[^%]/g, seq => chalk.magenta(seq))}`
|
||||
: ''}`,
|
||||
...(typeof format === 'string' ? [] : [format]).concat(rest)
|
||||
);
|
||||
},
|
||||
error(...args) {
|
||||
const [format, ...rest] = args;
|
||||
console.error(
|
||||
`${chalk.grey('[Semantic release]:')} ${chalk.red(format instanceof Error ? format.stack : format)}`,
|
||||
...rest.map(arg => chalk.red(arg instanceof Error ? arg.stack : arg))
|
||||
`${chalk.grey('[Semantic release]:')}${typeof format === 'string' ? ` ${chalk.red(format)}` : ''}`,
|
||||
...(typeof format === 'string' ? [] : [format]).concat(rest)
|
||||
);
|
||||
},
|
||||
};
|
||||
|
||||
Vendored
+3
-1
@@ -1,3 +1,5 @@
|
||||
module.exports = function(config, options, cb) {
|
||||
cb(new Error('a'));
|
||||
const error = new Error('a');
|
||||
error.errorProperty = 'errorProperty';
|
||||
cb(error);
|
||||
};
|
||||
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
const SemanticReleaseError = require('@semantic-release/error');
|
||||
|
||||
class InheritedError extends SemanticReleaseError {
|
||||
constructor(message, code, newProperty) {
|
||||
super(message);
|
||||
Error.captureStackTrace(this, this.constructor);
|
||||
this.name = this.constructor.name;
|
||||
this.code = code;
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = function(config, options, cb) {
|
||||
cb(new InheritedError('Inherited error', 'EINHERITED'));
|
||||
};
|
||||
@@ -17,6 +17,7 @@ const env = {
|
||||
const cli = require.resolve('../bin/semantic-release');
|
||||
const noop = require.resolve('../src/lib/plugin-noop');
|
||||
const pluginError = require.resolve('./fixtures/plugin-error-a');
|
||||
const pluginInheritedError = require.resolve('./fixtures/plugin-error-inherited');
|
||||
|
||||
test.before(async t => {
|
||||
await mockServer.start();
|
||||
@@ -35,7 +36,6 @@ test.beforeEach(async t => {
|
||||
});
|
||||
|
||||
test.afterEach.always(async t => {
|
||||
console.log();
|
||||
// Restore process.env
|
||||
process.env = Object.assign({}, t.context.env);
|
||||
// Restore the current working directory
|
||||
@@ -574,7 +574,7 @@ test.serial('Run via JS API', async t => {
|
||||
await semanticRelease({githubToken, verifyConditions: [noop, noop], debug: true});
|
||||
|
||||
t.true(t.context.log.calledWithMatch(/Published Github release: /, new RegExp(`release-url/${version}`)));
|
||||
t.true(t.context.log.calledWithMatch(/Publishing version %s to npm registry %s/, version, registry.uri));
|
||||
t.true(t.context.log.calledWithMatch(/Publishing version .* to npm registry/, version, registry.uri));
|
||||
|
||||
// Verify package.json and has been updated
|
||||
t.is((await readJson('./package.json')).version, version);
|
||||
@@ -615,7 +615,7 @@ test.serial('Returns and error code if NPM token is invalid', async t => {
|
||||
t.is(code, 1);
|
||||
});
|
||||
|
||||
test.serial('Log unexpected errors from plugins', async t => {
|
||||
test.serial('Log unexpected errors from plugins and exit with 1', async t => {
|
||||
const packageName = 'test-module-9';
|
||||
const repo = 'test-repo';
|
||||
// Create a git repository, set the current working directory at the root of the repo
|
||||
@@ -634,11 +634,39 @@ test.serial('Log unexpected errors from plugins', async t => {
|
||||
await gitCommits(['feat: Initial commit']);
|
||||
t.log('$ semantic-release');
|
||||
let {stderr, code} = await execa(cli, [], {env, reject: false});
|
||||
// Verify the type and message are logged
|
||||
t.regex(stderr, /Error: a/);
|
||||
// Verify the the stacktrace is logged
|
||||
t.regex(stderr, new RegExp(pluginError));
|
||||
// Verify the Error properties are logged
|
||||
t.regex(stderr, /errorProperty: 'errorProperty'/);
|
||||
t.is(code, 1);
|
||||
});
|
||||
|
||||
test.serial('Log errors inheriting SemanticReleaseError and exit with 0', async t => {
|
||||
const packageName = 'test-module-10';
|
||||
const repo = 'test-repo';
|
||||
// Create a git repository, set the current working directory at the root of the repo
|
||||
t.log('Create git repository and package.json');
|
||||
await gitRepo();
|
||||
// Create package.json in repository root
|
||||
await writeJson('./package.json', {
|
||||
name: packageName,
|
||||
version: '0.0.0-dev',
|
||||
repository: {url: `git+https://github.com/${repo}/${packageName}`},
|
||||
release: {githubUrl: mockServer.url, verifyConditions: pluginInheritedError},
|
||||
});
|
||||
|
||||
/** Initial release **/
|
||||
t.log('Commit a feature');
|
||||
await gitCommits(['feat: Initial commit']);
|
||||
t.log('$ semantic-release');
|
||||
let {stdout, code} = await execa(cli, [], {env, reject: false});
|
||||
// Verify the type and message are logged
|
||||
t.regex(stdout, /EINHERITED Inherited error/);
|
||||
t.is(code, 0);
|
||||
});
|
||||
|
||||
test.serial('CLI returns error code and prints help if called with a command', async t => {
|
||||
t.log('$ semantic-release pre');
|
||||
let {stdout, code} = await execa(cli, ['pre'], {env, reject: false});
|
||||
|
||||
+19
-8
@@ -1,5 +1,5 @@
|
||||
import test from 'ava';
|
||||
import {stub} from 'sinon';
|
||||
import {stub, match} from 'sinon';
|
||||
import logger from '../src/lib/logger';
|
||||
|
||||
test.beforeEach(t => {
|
||||
@@ -20,18 +20,29 @@ test.serial('Basic log', t => {
|
||||
t.true(t.context.error.calledWithMatch(/.*test error/));
|
||||
});
|
||||
|
||||
test.serial('Log object', t => {
|
||||
const obj = {a: 1, b: '2'};
|
||||
logger.log(obj);
|
||||
logger.error(obj);
|
||||
|
||||
t.true(t.context.log.calledWithMatch(match.string, obj));
|
||||
t.true(t.context.error.calledWithMatch(match.string, obj));
|
||||
});
|
||||
|
||||
test.serial('Log with string formatting', t => {
|
||||
logger.log('test log %s', 'log value');
|
||||
logger.error('test error %s', 'error value');
|
||||
|
||||
t.true(t.context.log.calledWithMatch(/.*test log %s/, 'log value'));
|
||||
t.true(t.context.error.calledWithMatch(/.*test error %s/, 'error value'));
|
||||
t.true(t.context.log.calledWithMatch(/.*test log/, 'log value'));
|
||||
t.true(t.context.error.calledWithMatch(/.*test error/, 'error value'));
|
||||
});
|
||||
|
||||
test.serial('Log with error stacktrace', t => {
|
||||
logger.error(new Error('error message'));
|
||||
logger.error('test error %s', new Error('other error message'));
|
||||
test.serial('Log with error stacktrace and properties', t => {
|
||||
const error = new Error('error message');
|
||||
logger.error(error);
|
||||
const otherError = new Error('other error message');
|
||||
logger.error('test error %O', otherError);
|
||||
|
||||
t.true(t.context.error.calledWithMatch(/.*test error %s/, /Error: other error message(\s|.)*?logger\.test\.js/));
|
||||
t.true(t.context.error.calledWithMatch(/Error: error message(\s|.)*?logger\.test\.js/));
|
||||
t.true(t.context.error.calledWithMatch(match.string, error));
|
||||
t.true(t.context.error.calledWithMatch(/.*test error/, otherError));
|
||||
});
|
||||
|
||||
@@ -2,12 +2,12 @@ import test from 'ava';
|
||||
import SemanticReleaseError from '@semantic-release/error';
|
||||
import verify from '../src/lib/verify-pkg';
|
||||
|
||||
test.only('Verify name and repository', t => {
|
||||
test('Verify name and repository', t => {
|
||||
// Call the verify module with package
|
||||
t.notThrows(() => verify({name: 'package', repository: {url: 'http://github.com/whats/up.git'}}));
|
||||
});
|
||||
|
||||
test.only('Return error for missing package name', t => {
|
||||
test('Return error for missing package name', t => {
|
||||
// Call the verify module with package
|
||||
const error = t.throws(() => verify({repository: {url: 'http://github.com/whats/up.git'}}));
|
||||
// Verify error code and type
|
||||
@@ -15,7 +15,7 @@ test.only('Return error for missing package name', t => {
|
||||
t.true(error instanceof SemanticReleaseError);
|
||||
});
|
||||
|
||||
test.only('Return error for missing repository', t => {
|
||||
test('Return error for missing repository', t => {
|
||||
// Call the verify module with package
|
||||
const error = t.throws(() => verify({name: 'package'}));
|
||||
// Verify error code and type
|
||||
@@ -23,7 +23,7 @@ test.only('Return error for missing repository', t => {
|
||||
t.true(error instanceof SemanticReleaseError);
|
||||
});
|
||||
|
||||
test.only('Return error for missing repository url', t => {
|
||||
test('Return error for missing repository url', t => {
|
||||
// Call the verify module with package
|
||||
const error = t.throws(() => verify({name: 'package', repository: {}}));
|
||||
// Verify error code and type
|
||||
|
||||
Reference in New Issue
Block a user