不要怂,就是干,撸起袖子干!

Commit 584b6f74 by Leroy Witteveen Committed by Jan Aagaard Meier

fix(errors): Add missing captureStackTrace for errors. (#7779)

1 parent e3fa4d61
Showing with 58 additions and 3 deletions
...@@ -24,6 +24,7 @@ class SequelizeScopeError extends BaseError { ...@@ -24,6 +24,7 @@ class SequelizeScopeError extends BaseError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeScopeError'; this.name = 'SequelizeScopeError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.SequelizeScopeError = SequelizeScopeError; exports.SequelizeScopeError = SequelizeScopeError;
...@@ -56,6 +57,7 @@ class ValidationError extends BaseError { ...@@ -56,6 +57,7 @@ class ValidationError extends BaseError {
} else if (this.errors.length > 0 && this.errors[0].message) { } else if (this.errors.length > 0 && this.errors[0].message) {
this.message = this.errors.map(err => err.type + ': ' + err.message).join(',\n'); this.message = this.errors.map(err => err.type + ': ' + err.message).join(',\n');
} }
Error.captureStackTrace(this, this.constructor);
} }
/** /**
...@@ -100,6 +102,7 @@ class OptimisticLockError extends BaseError { ...@@ -100,6 +102,7 @@ class OptimisticLockError extends BaseError {
* @type {object} * @type {object}
*/ */
this.where = options.where; this.where = options.where;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.OptimisticLockError = OptimisticLockError; exports.OptimisticLockError = OptimisticLockError;
...@@ -124,6 +127,7 @@ class DatabaseError extends BaseError { ...@@ -124,6 +127,7 @@ class DatabaseError extends BaseError {
* @type {string} * @type {string}
*/ */
this.sql = parent.sql; this.sql = parent.sql;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.DatabaseError = DatabaseError; exports.DatabaseError = DatabaseError;
...@@ -135,6 +139,7 @@ class TimeoutError extends DatabaseError { ...@@ -135,6 +139,7 @@ class TimeoutError extends DatabaseError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeTimeoutError'; this.name = 'SequelizeTimeoutError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.TimeoutError = TimeoutError; exports.TimeoutError = TimeoutError;
...@@ -157,6 +162,7 @@ class UniqueConstraintError extends ValidationError { ...@@ -157,6 +162,7 @@ class UniqueConstraintError extends ValidationError {
this.parent = options.parent; this.parent = options.parent;
this.original = options.parent; this.original = options.parent;
this.sql = options.parent.sql; this.sql = options.parent.sql;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.UniqueConstraintError = UniqueConstraintError; exports.UniqueConstraintError = UniqueConstraintError;
...@@ -177,6 +183,7 @@ class ForeignKeyConstraintError extends DatabaseError { ...@@ -177,6 +183,7 @@ class ForeignKeyConstraintError extends DatabaseError {
this.table = options.table; this.table = options.table;
this.value = options.value; this.value = options.value;
this.index = options.index; this.index = options.index;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.ForeignKeyConstraintError = ForeignKeyConstraintError; exports.ForeignKeyConstraintError = ForeignKeyConstraintError;
...@@ -196,6 +203,7 @@ class ExclusionConstraintError extends DatabaseError { ...@@ -196,6 +203,7 @@ class ExclusionConstraintError extends DatabaseError {
this.constraint = options.constraint; this.constraint = options.constraint;
this.fields = options.fields; this.fields = options.fields;
this.table = options.table; this.table = options.table;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.ExclusionConstraintError = ExclusionConstraintError; exports.ExclusionConstraintError = ExclusionConstraintError;
...@@ -209,6 +217,7 @@ class UnknownConstraintError extends DatabaseError { ...@@ -209,6 +217,7 @@ class UnknownConstraintError extends DatabaseError {
super(parent); super(parent);
this.name = 'SequelizeUnknownConstraintError'; this.name = 'SequelizeUnknownConstraintError';
this.message = message || 'The specified constraint does not exist'; this.message = message || 'The specified constraint does not exist';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.UnknownConstraintError = UnknownConstraintError; exports.UnknownConstraintError = UnknownConstraintError;
...@@ -228,6 +237,7 @@ class ValidationErrorItem { ...@@ -228,6 +237,7 @@ class ValidationErrorItem {
this.type = type || null; this.type = type || null;
this.path = path || null; this.path = path || null;
this.value = value !== undefined ? value : null; this.value = value !== undefined ? value : null;
//This doesn't need captureStackTrace because its not a subclass of Error
} }
} }
exports.ValidationErrorItem = ValidationErrorItem; exports.ValidationErrorItem = ValidationErrorItem;
...@@ -245,6 +255,7 @@ class ConnectionError extends BaseError { ...@@ -245,6 +255,7 @@ class ConnectionError extends BaseError {
*/ */
this.parent = parent; this.parent = parent;
this.original = parent; this.original = parent;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.ConnectionError = ConnectionError; exports.ConnectionError = ConnectionError;
...@@ -256,6 +267,7 @@ class ConnectionRefusedError extends ConnectionError { ...@@ -256,6 +267,7 @@ class ConnectionRefusedError extends ConnectionError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeConnectionRefusedError'; this.name = 'SequelizeConnectionRefusedError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.ConnectionRefusedError = ConnectionRefusedError; exports.ConnectionRefusedError = ConnectionRefusedError;
...@@ -267,6 +279,7 @@ class AccessDeniedError extends ConnectionError { ...@@ -267,6 +279,7 @@ class AccessDeniedError extends ConnectionError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeAccessDeniedError'; this.name = 'SequelizeAccessDeniedError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.AccessDeniedError = AccessDeniedError; exports.AccessDeniedError = AccessDeniedError;
...@@ -278,6 +291,7 @@ class HostNotFoundError extends ConnectionError { ...@@ -278,6 +291,7 @@ class HostNotFoundError extends ConnectionError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeHostNotFoundError'; this.name = 'SequelizeHostNotFoundError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.HostNotFoundError = HostNotFoundError; exports.HostNotFoundError = HostNotFoundError;
...@@ -289,6 +303,7 @@ class HostNotReachableError extends ConnectionError { ...@@ -289,6 +303,7 @@ class HostNotReachableError extends ConnectionError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeHostNotReachableError'; this.name = 'SequelizeHostNotReachableError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.HostNotReachableError = HostNotReachableError; exports.HostNotReachableError = HostNotReachableError;
...@@ -300,6 +315,7 @@ class InvalidConnectionError extends ConnectionError { ...@@ -300,6 +315,7 @@ class InvalidConnectionError extends ConnectionError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeInvalidConnectionError'; this.name = 'SequelizeInvalidConnectionError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.InvalidConnectionError = InvalidConnectionError; exports.InvalidConnectionError = InvalidConnectionError;
...@@ -311,6 +327,7 @@ class ConnectionTimedOutError extends ConnectionError { ...@@ -311,6 +327,7 @@ class ConnectionTimedOutError extends ConnectionError {
constructor(parent) { constructor(parent) {
super(parent); super(parent);
this.name = 'SequelizeConnectionTimedOutError'; this.name = 'SequelizeConnectionTimedOutError';
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.ConnectionTimedOutError = ConnectionTimedOutError; exports.ConnectionTimedOutError = ConnectionTimedOutError;
...@@ -323,6 +340,7 @@ class InstanceError extends BaseError { ...@@ -323,6 +340,7 @@ class InstanceError extends BaseError {
super(message); super(message);
this.name = 'SequelizeInstanceError'; this.name = 'SequelizeInstanceError';
this.message = message; this.message = message;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.InstanceError = InstanceError; exports.InstanceError = InstanceError;
...@@ -335,6 +353,7 @@ class EmptyResultError extends BaseError { ...@@ -335,6 +353,7 @@ class EmptyResultError extends BaseError {
super(message); super(message);
this.name = 'SequelizeEmptyResultError'; this.name = 'SequelizeEmptyResultError';
this.message = message; this.message = message;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.EmptyResultError = EmptyResultError; exports.EmptyResultError = EmptyResultError;
...@@ -347,6 +366,7 @@ class EagerLoadingError extends BaseError { ...@@ -347,6 +366,7 @@ class EagerLoadingError extends BaseError {
super(message); super(message);
this.name = 'SequelizeEagerLoadingError'; this.name = 'SequelizeEagerLoadingError';
this.message = message; this.message = message;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.EagerLoadingError = EagerLoadingError; exports.EagerLoadingError = EagerLoadingError;
...@@ -359,6 +379,7 @@ class AssociationError extends BaseError { ...@@ -359,6 +379,7 @@ class AssociationError extends BaseError {
super(message); super(message);
this.name = 'SequelizeAssociationError'; this.name = 'SequelizeAssociationError';
this.message = message; this.message = message;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.AssociationError = AssociationError; exports.AssociationError = AssociationError;
...@@ -370,6 +391,7 @@ class QueryError extends BaseError { ...@@ -370,6 +391,7 @@ class QueryError extends BaseError {
super(message); super(message);
this.name = 'SequelizeQueryError'; this.name = 'SequelizeQueryError';
this.message = message; this.message = message;
Error.captureStackTrace(this, this.constructor);
} }
} }
exports.QueryError = QueryError; exports.QueryError = QueryError;
...@@ -4,9 +4,39 @@ const errors = require('../../lib/errors'); ...@@ -4,9 +4,39 @@ const errors = require('../../lib/errors');
const expect = require('chai').expect; const expect = require('chai').expect;
describe('errors', () => { describe('errors', () => {
it('should maintain stack trace', () => { it('should maintain stack trace with message', () => {
const errorsWithMessage = [
'BaseError', 'ValidationError', 'UnknownConstraintError', 'InstanceError',
'EmptyResultError', 'EagerLoadingError', 'AssociationError', 'QueryError'
];
errorsWithMessage.forEach(errorName => {
function throwError() {
throw new errors[errorName]('this is a message');
}
let err;
try {
throwError();
} catch (error) {
err = error;
}
expect(err).to.exist;
const stackParts = err.stack.split('\n');
const fullErrorName = 'Sequelize' + errorName;
expect(stackParts[0]).to.equal(fullErrorName + ': this is a message');
expect(stackParts[1]).to.match(/^ at throwError \(.*errors.test.js:\d+:\d+\)$/);
});
});
it('should maintain stack trace without message', () => {
const errorsWithoutMessage = [
'ConnectionError', 'ConnectionRefusedError', 'ConnectionTimedOutError',
'AccessDeniedError', 'HostNotFoundError', 'HostNotReachableError', 'InvalidConnectionError'
];
errorsWithoutMessage.forEach(errorName => {
function throwError() { function throwError() {
throw new errors.ValidationError('this is a message'); throw new errors[errorName](null);
} }
let err; let err;
try { try {
...@@ -16,7 +46,10 @@ describe('errors', () => { ...@@ -16,7 +46,10 @@ describe('errors', () => {
} }
expect(err).to.exist; expect(err).to.exist;
const stackParts = err.stack.split('\n'); const stackParts = err.stack.split('\n');
expect(stackParts[0]).to.equal('SequelizeValidationError: this is a message');
const fullErrorName = 'Sequelize' + errorName;
expect(stackParts[0]).to.equal(fullErrorName);
expect(stackParts[1]).to.match(/^ at throwError \(.*errors.test.js:\d+:\d+\)$/); expect(stackParts[1]).to.match(/^ at throwError \(.*errors.test.js:\d+:\d+\)$/);
}); });
});
}); });
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!