Puis-je définir des types personnalisés pour les exceptions définies par l’utilisateur en JavaScript ? Si je peux, comment pourrais-je faire il ?
Réponses
Trop de publicités?Oui. Vous pouvez jeter tout ce que vous voulez : entiers, chaînes, des objets, quel que soit. Si vous voulez jeter un objet, puis simplement créer un nouvel objet, tout comme vous en créer un dans d’autres circonstances et puis le jeter. Référence de Javascript de Mozilla a plusieurs exemples.
Voici comment vous pouvez créer des messages d'erreur personnalisés avec totalement identique à l'natif Error
s'comportement. Cette technique ne fonctionne que sur Chrome et node.js pour l'instant. Aussi je ne vous recommande pas de l'utiliser si vous ne comprenez pas ce qu'il fait.
Error.createCustromConstructor = (function() {
function define(obj, prop, value) {
Object.defineProperty(obj, prop, {
value: value,
configurable: true,
enumerable: false,
writable: true
});
}
return function(name, init, proto) {
var CustomError;
proto = proto || {};
function build(message) {
var self = this instanceof CustomError
? this
: Object.create(CustomError.prototype);
Error.apply(self, arguments);
Error.captureStackTrace(self, CustomError);
if (message != undefined) {
define(self, 'message', String(message));
}
define(self, 'arguments', undefined);
define(self, 'type', undefined);
if (typeof init == 'function') {
init.apply(self, arguments);
}
return self;
}
eval('CustomError = function ' + name + '() {' +
'return build.apply(this, arguments); }');
CustomError.prototype = Object.create(Error.prototype);
define(CustomError.prototype, 'constructor', CustomError);
for (var key in proto) {
define(CustomError.prototype, key, proto[key]);
}
Object.defineProperty(CustomError.prototype, 'name', { value: name });
return CustomError;
}
})();
Comme un reasult nous obtenons
/**
* name The name of the constructor name
* init User-defined initialization function
* proto It's enumerable members will be added to
* prototype of created constructor
**/
Error.createCustromConstructor = function(name, init, proto)
Ensuite, vous pouvez l'utiliser comme ceci:
var NotImplementedError = Error.createCustromConstructor('NotImplementedError');
Et utiliser NotImplementedError
comme vous le feriez Error
:
throw new NotImplementedError();
var err = new NotImplementedError();
var err = NotImplementedError('Not yet...');
Et il va se comporter qui est attendu:
err instanceof NotImplementedError // -> true
err instanceof Error // -> true
NotImplementedError.prototype.isPrototypeOf(err) // -> true
Error.prototype.isPrototypeOf(err) // -> true
err.constructor.name // -> NotImplementedError
err.name // -> NotImplementedError
err.message // -> Not yet...
err.toString() // -> NotImplementedError: Not yet...
err.stack // -> works fine!
Remarque, c' error.stack
travaux absolutle correcte et ne comprennent NotImplementedError
appel du constructeur (grâce à v8 Error.captureStackTrace()
).
Remarque. Il est laid eval()
. La seule raison pour laquelle il est utilisé pour obtenir de bons err.constructor.name
. Si vous n'en avez pas besoin, vous pouvez un peu simplifier les choses.