Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support diffs #7

Closed
wants to merge 11 commits into from
14 changes: 13 additions & 1 deletion lib/assertThat.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
'use strict';

var q = require('q');
var _ = require('lodash');
var AssertionError = require('assertion-error')
, Description = require('./Description')
;
Expand All @@ -25,7 +26,18 @@ function assertThat(reason, actual, matcher) {
.appendDescriptionOf(matcher)
.append('\n but: ');
matcher.describeMismatch(actual, description);
throw new AssertionError(description.get(), {}, assertThat);

var errorProperties = {};
if (_.isFunction(matcher.getExpectedForDiff) &&
_.isFunction(matcher.formatActualForDiff)) {
errorProperties = {
showDiff: true,
expected: matcher.getExpectedForDiff(),
actual: matcher.formatActualForDiff(actual)
};
}

throw new AssertionError(description.get(), errorProperties, assertThat);
}
}

Expand Down
4 changes: 3 additions & 1 deletion lib/matchers/Is.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,9 @@ var Is = acceptingMatcher(function Is(innerMatcher) {
},
describeMismatch: function (value, description) {
return innerMatcher.describeMismatch(value, description);
}
},
getExpectedForDiff: innerMatcher.getExpectedForDiff,
formatActualForDiff: innerMatcher.formatActualForDiff
});
});

Expand Down
4 changes: 3 additions & 1 deletion lib/matchers/IsEqual.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,9 @@ function IsEqual(expectedValue) {
},
describeTo: function (description) {
description.appendValue(expectedValue);
}
},
getExpectedForDiff: function () { return expectedValue; },
formatActualForDiff: function (actual) { return actual; }
});
}

Expand Down
6 changes: 6 additions & 0 deletions lib/matchers/IsObjectWithProperties.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,12 @@ function IsObjectWithProperties(properties) {
.append(' ');
return propertyMatchers[key].describeMismatch(actual[key], description);
});
},
getExpectedForDiff: function () {
return properties;
},
formatActualForDiff: function (actual) {
return actual;
}
});
}
Expand Down
4 changes: 3 additions & 1 deletion lib/matchers/SubstringMatcher.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,9 @@ function SubstringMatcher(substring, relation, matchesString) {
description
.append('was ')
.appendValue(actual);
}
},
getExpectedForDiff: function () { return substring; },
formatActualForDiff: function (actual) { return actual; }
});
}

Expand Down
19 changes: 18 additions & 1 deletion lib/promiseThat.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
var q = require('q');
var AssertionError = require('assertion-error');
var Description = require('./Description');
var _ = require('lodash');

function promiseThat(reason, actual, matcher) {
if (arguments.length === 2) {
Expand All @@ -19,7 +20,23 @@ function promiseThat(reason, actual, matcher) {
.appendDescriptionOf(matcher)
.append('\n but: ');
return q(matcher.describeMismatch(actual, description)).then(function () {
throw new AssertionError(description.get(), {}, promiseThat);
if (!_.isFunction(matcher.getExpectedForDiff) ||
!_.isFunction(matcher.formatActualForDiff)) {
return {};
}

return q.all([
matcher.getExpectedForDiff(),
matcher.formatActualForDiff(actual)
]).spread(function (expected, actual) {
return {
showDiff: true,
expected: expected,
actual: actual
};
});
}).then(function (errorProperties) {
throw new AssertionError(description.get(), errorProperties, promiseThat);
});
}
});
Expand Down
4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -41,10 +41,10 @@
"grunt-contrib-nodeunit": "^0.2.2",
"grunt-contrib-uglify": "^0.3.3",
"grunt-contrib-watch": "^0.5.3",
"grunt-mocha-test": "^0.12.1",
"grunt-mocha-test": "^0.12.4",
"jshint-stylish": "^0.1.5",
"load-grunt-tasks": "^0.2.1",
"mocha": "^1.21.4",
"mocha": "^2.0.1",
"time-grunt": "^0.2.10"
},
"dependencies": {
Expand Down
22 changes: 22 additions & 0 deletions test/assertThatSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,28 @@ describe('assertThat', function () {
assertEquals(thrown.message , 'Assertion message\nExpected: Matcher description\n but: was "real value"');
});

it('should pass diff representations to AssertionError', function () {
var thrown;

var testMatcher = new TestMatcher(function () { return false; });
testMatcher.getExpectedForDiff = function () {
return 'expected for diff';
};
testMatcher.formatActualForDiff = function (actual) {
return 'actual for diff: ' + actual;
};

try {
assertThat('actual value', testMatcher);
}
catch (e) {
thrown = e;
}

assertEquals(thrown.expected, 'expected for diff');
assertEquals(thrown.actual, 'actual for diff: actual value');
});

it('should throw if matcher returns a promise', function () {
var thrown;

Expand Down
10 changes: 10 additions & 0 deletions test/matchers/IsObjectWithPropertiesSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,16 @@ describe('IsObjectWithProperties', function () {
});
});

it('should format actual for diff', function () {
var simple = IsObjectWithProperties.hasProperties();
__.assertThat(simple.formatActualForDiff({a: 1}), __.equalTo({a: 1}));
});

it('should provide expected for diff', function () {
var simple = IsObjectWithProperties.hasProperties({a: 1});
__.assertThat(simple.getExpectedForDiff(), __.equalTo({a: 1}));
});

describe('with a promising matcher', function () {
beforeEach(function () {
sut = hasProperties({
Expand Down
9 changes: 9 additions & 0 deletions test/matchers/SubstringMatcherSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ var AssertionError = require('assertion-error')
, __ = require('../../lib/hamjest')
, assertTrue = require('../asserts').assertTrue
, assertFalse = require('../asserts').assertFalse
, assertEquals = require('../asserts').assertEquals
;

describe('SubstringMatcher', function () {
Expand Down Expand Up @@ -40,6 +41,14 @@ describe('SubstringMatcher', function () {
assertFalse(sut.matches(5));
});

it('should provide expected for diff', function () {
assertEquals('a value', sut.getExpectedForDiff());
});

it('should format actual for diff', function() {
assertEquals('foo', sut.formatActualForDiff('foo'));
});

describe('description', function () {
var description;

Expand Down
23 changes: 23 additions & 0 deletions test/promiseThatSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -157,4 +157,27 @@ describe('promiseThat', function () {

deferred.resolve();
});

it('should pass diff representations to AssertionError', function (done) {
var testMatcher = new TestMatcher(function () { return false; });
testMatcher.getExpectedForDiff = function () {
return 'expected for diff';
};
testMatcher.formatActualForDiff = function (actual) {
return q('actual for diff: ' + actual);
};

promiseThat('actual value', testMatcher).done(
function () {
fail('Should not be fulfilled');
},
function (reason) {
__.assertThat(reason, __.hasProperties({
expected: 'expected for diff',
actual: 'actual for diff: actual value'
}));
done();
}
);
});
});