Comparing version 0.2.0 to 0.4.0
{ | ||
"name": "lazy-ass", | ||
"main": "index.js", | ||
"version": "0.2.0", | ||
"version": "0.4.0", | ||
"homepage": "https://github.com/bahmutov/lazy-ass", | ||
@@ -6,0 +6,0 @@ "license": "MIT", |
30
index.js
@@ -17,2 +17,5 @@ (function initLazyAss() { | ||
} | ||
if (arg instanceof Error) { | ||
return total + arg.name + ' ' + arg.message; | ||
} | ||
return total + JSON.stringify(arg, null, 2); | ||
@@ -23,14 +26,29 @@ }, ''); | ||
var lazyAss = function lazyAss(condition) { | ||
function lazyAssLogic(condition) { | ||
var fn = typeof condition === 'function' ? condition : null; | ||
if (fn) { | ||
condition = fn(); | ||
} | ||
if (!condition) { | ||
var args = [].slice.call(arguments, 1); | ||
throw new Error(formMessage(args)); | ||
if (fn) { | ||
args.unshift(fn.toString()); | ||
} | ||
return new Error(formMessage(args)); | ||
} | ||
} | ||
var lazyAss = function lazyAss() { | ||
var err = lazyAssLogic.apply(null, arguments); | ||
if (err) { | ||
throw err; | ||
} | ||
}; | ||
var lazyAssync = function lazyAssync(condition) { | ||
if (!condition) { | ||
var args = [].slice.call(arguments, 1); | ||
var lazyAssync = function lazyAssync() { | ||
var err = lazyAssLogic.apply(null, arguments); | ||
if (err) { | ||
setTimeout(function () { | ||
throw new Error(formMessage(args)); | ||
throw err; | ||
}, 0); | ||
@@ -37,0 +55,0 @@ } |
{ | ||
"name": "lazy-ass", | ||
"description": "Lazy assertions without performance penalty", | ||
"version": "0.2.0", | ||
"version": "0.4.0", | ||
"author": "Gleb Bahmutov <gleb.bahmutov@gmail.com>", | ||
@@ -6,0 +6,0 @@ "bugs": { |
@@ -29,2 +29,15 @@ # lazy-ass | ||
Concatenates strings, stringifies objects, calls functions - only if | ||
condition is false. | ||
```js | ||
function environment() { | ||
// returns string | ||
} | ||
var user = {} // an object | ||
lazyAsync(condition, 'something went wrong for', user, 'in', environment); | ||
// throws an error with message equivalent of | ||
// 'something went wrong for ' + JSON.stringify(user) + ' in ' + environment() | ||
``` | ||
## Why? | ||
@@ -86,2 +99,44 @@ | ||
## Predicate function as a condition | ||
Typically, JavaScript evaluates the condition expression first, then calls *lazyAss*. | ||
This means the function itself sees only the true / false result, and not the expression | ||
itself. This makes makes the error messages cryptic | ||
lazyAss(2 + 2 === 5); | ||
// Error | ||
We usually get around this by giving at least one additional message argument to | ||
explain the condition tested | ||
lazyAss(2 + 2 === 5, 'addition') | ||
// Error: addition | ||
*lazyAss* has a better solution: if you give a function that evaluates the condition | ||
expression, if the function returns false, the error message will include the source | ||
of the function, making the extra arguments unnecessary | ||
lazyAss(function () { return 2 + 2 === 5; }); | ||
// Error: function () { return 2 + 2 === 5; } | ||
The condition function has access to any variables in the scope, making it extremely | ||
powerful | ||
var foo = 2, bar = 2; | ||
lazyAss(function () { return foo + bar === 5; }); | ||
// Error: function () { return foo + bar === 5; } | ||
In practical terms, I recommend using separate predicates function and | ||
passing relevant values to the *lazyAss* function. Remember, there is no performance | ||
penalty! | ||
var foo = 2, bar = 2; | ||
function isValidPair() { | ||
return foo + bar === 5; | ||
} | ||
lazyAss(isValidPair, 'foo', foo, 'bar', bar); | ||
// Error: function isValidPair() { | ||
// return foo + bar === 5; | ||
// } foo 2 bar 2 | ||
### Small print | ||
@@ -88,0 +143,0 @@ |
@@ -80,3 +80,67 @@ /* global lazyAss */ | ||
}); | ||
it('takes error name and message', function () { | ||
expect(function () { | ||
lazyAss(false, new Error('hi there')); | ||
}).to.throwException(function (err) { | ||
expect(err.message).to.contain('Error'); | ||
expect(err.message).to.contain('hi there'); | ||
}); | ||
}); | ||
}); | ||
describe('function as condition', function () { | ||
it('evaluates the function', function () { | ||
var called; | ||
function condition() { called = true; return true; } | ||
lazyAss(condition); | ||
expect(called).to.be(true); | ||
}); | ||
it('no result is failure', function () { | ||
function noreturn() {} | ||
expect(function () { | ||
lazyAss(noreturn); | ||
}).to.throwError(); | ||
}); | ||
it('adds condition function source to message', function () { | ||
function myCondition() {} | ||
expect(function () { | ||
lazyAss(myCondition); | ||
}).to.throwException(/myCondition/); | ||
}); | ||
it('allows anonymous functions', function () { | ||
var called; | ||
lazyAss(function() { return true; }); | ||
lazyAss(function() { return true; }, 'everything is ok'); | ||
lazyAss(function() { called = true; return true; }, 'everything is ok'); | ||
expect(called).to.be(true); | ||
expect(function () { | ||
lazyAss(function () {}); | ||
}).to.throwError(); | ||
}); | ||
it('has access via closure', function () { | ||
var foo = 2, bar = 3; | ||
expect(function () { | ||
lazyAss(function () { return foo + bar === 6; }, 'addition'); | ||
}).to.throwException(function (err) { | ||
expect(err.message).to.contain('foo + bar'); | ||
expect(err.message).to.contain('addition'); | ||
}); | ||
}); | ||
it('example', function () { | ||
var foo = 2, bar = 2; | ||
function isValidPair() { | ||
return foo + bar === 4; | ||
} | ||
lazyAss(isValidPair, 'foo', foo, 'bar', bar); | ||
}); | ||
}); | ||
}); |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
21870
367
190