16

I am learning about testing in Node.js using mocha and the assert module. assert has these types of methods:

assert.equal();
assert.deepEqual();
assert.deepStrict();
assert.strict();
assert.ok(); // Is the value true?

And then there are some opposites:

assert.notEqual();
assert.notDeepEqual();
assert.notDeepStrict();
assert.notStrict();

But there one missing... Why is there not a notOk() method for testing if the resulting value is false or not?

This got me thinking that maybe there is something fundamental I am missing about unit testing in general, in that maybe I should only ever be testing if values are true and never false...

For now, I have simply been doing this to test for falsey statements:

assert.ok(!myValue);

Is that how you are supposed to do it? Again, why isn't there just a notOk() method since all the other methods have a not version?

Jake Wilson
  • 88,616
  • 93
  • 252
  • 370
  • You can also check out the Chai assertion library for more methods; they have an `isNotOk` function: http://chaijs.com/api/assert/#method_isnotok – hackerrdave Nov 10 '16 at 04:59

1 Answers1

7

If you look at the docs, it notes that .ok(value, message) is equivalent to assert.equal(!!value, true, message). This appears to simply be a convenience function.

It should be noted that while the function is called ok(), that does not mean that it is expecting a true value from your code. It is expecting a statement to which you want to test the truthiness of. So while your usage of !myValue is valid, I think it would be more appropriate to write:

assert.ok(myValue === false);

The above makes sense semantically, as you are still testing the truthiness of your expression, it just so happens that you are expecting it to be false. To have included a notOk() function would imply some ambiguous meaning. Not OK implies failure, and so the failure of a notOk function might have just seemed a little convoluted.

As for the other methods having their not equivalents, I think the language is still meaningful. Saying notEqual is implying that you are testing specifically for an inequality, while notOk doesn't really make sense. Personally I would just leave out using ok() all together, as ok in and of itself it quite ambiguous anyway.

If you really feel the need, you could simply write your own convenience function too.


I think it is also worth mentioning that this is the source:

// 4. Pure assertion tests whether a value is truthy, as determined
// by !!guard.
// assert.ok(guard, message_opt);
// This statement is equivalent to assert.equal(true, !!guard,
// message_opt);. To test strictly for the value true, use
// assert.strictEqual(true, guard, message_opt);.

function ok(value, message) {
    if (!value) fail(value, true, message, '==', assert.ok);
}
assert.ok = ok;
Matt Way
  • 32,319
  • 10
  • 79
  • 85
  • 8
    If you are going to use `assert.ok(myValue === false);` then why not just use `assert.equal(myValue, false);` ? I know they are the same thing essentially. But it's weird that `.ok()` exists without `.notOk()` given that it's the same as `assert.equal(myValue,true);` – Jake Wilson Nov 10 '16 at 20:53