Skip to content
rluba edited this page Nov 1, 2014 · 4 revisions

Writing custom matchers

Most assertions can be accomplished using existing matchers. Especially hasProperty and hasProperties can be used to generate assertions that provide clear error descriptions if they fail:

var person = {name: 13};
__.assertThat(person, __.hasProperties({
    name: __.string(),
    age: __.greaterThan(18)
}));

produces:

	AssertionError: 
	Expected: an object with {name: a string, age: a number greater than <18>}
	     but: name was a number (<13>), age was undefined

But sometimes it can be useful to create custom matchers for common assertions to make your tests more readable.

Matcher requirements

A matcher must provide three methods:

  • matches(actual) is called with the actual value given to the assertion and must return a truthy value if actual meets the expectations. Otherwise it must return a falsy value.

    If a matcher returns a promise instead, it is known as a promising matcher and may only be used with promiseThat. See Hamjest and Promises for details.

  • describeTo(description) should describe the matcher expectation using the provided description object. For example the closeTo matcher describes itself as:

     description
     	.append('a number within ')
     	.appendValue(delta)
     	.append(' of ')
     	.appendValue(threshold);
  • describeMismatch(actual, description) is called if actual did not match the expectation and should describe as detailed as possible why this value failed to match. This description is what sets Hamjest apart from many other assertion libraries as it helps developers understand why a test failed.

    For example closeTo adds the actual delta to the description:

     description
     	.appendValue(actual)
     	.append(' differed by ')
     	.appendValue(getDelta(actual));

Building on existing matchers

TODO