Skip to content

Commit

Permalink
Big refactor of unit tests; Added feature and integration tests; Fini…
Browse files Browse the repository at this point in the history
…shed bonus logic;
  • Loading branch information
sblausten committed Jul 29, 2017
1 parent 86f2680 commit 7cde9e6
Show file tree
Hide file tree
Showing 11 changed files with 416 additions and 116 deletions.
3 changes: 2 additions & 1 deletion SpecRunner.html
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,8 @@


<!-- include spec files here... -->
<script src="spec/features/playFrameSpec.js"></script>
<script src="spec/features/playSpec.js"></script>
<script src="spec/integration/ScoreCardSpec.js"></script>
<script src="spec/units/RollSpec.js"></script>
<script src="spec/units/FrameSpec.js"></script>
<script src="spec/units/GameSpec.js"></script>
Expand Down
14 changes: 7 additions & 7 deletions lib/jasmine-2.6.4/jasmine.css

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

14 changes: 0 additions & 14 deletions spec/features/playFrameSpec.js

This file was deleted.

35 changes: 35 additions & 0 deletions spec/features/playSpec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
'use strict';

describe('Play', function () {
it('updates the scorecard with correct frame scores after normal frame', function () {
var game, scorecard;
game = new Game();
spyOn(Math, 'random').and.returnValues(0.2, 0.6, 0.1);
game.play();
game.play();
game.play();
scorecard = game.getScoreCard();
expect(scorecard.getCard()).toEqual([[2, 5], [1]]);
});
it('updates the scorecard with correct frame scores after spare', function () {
var game, scorecard;
game = new Game();
spyOn(Math, 'random').and.returnValues(0.51, 0.9, 0.1);
game.play();
game.play();
game.play();
scorecard = game.getScoreCard();
expect(scorecard.getCard()).toEqual([[5, 5, 1], [1]]);
});
it('play a gutter game', function () {
var game, scorecard;
game = new Game();
spyOn(Math, 'random').and.returnValue(0);
for (var i = 0; i < 20; i++) {
game.play();
}
scorecard = game.getScoreCard();
expect(scorecard.getCard().length).toEqual(10);
expect(game.getTotalScore()).toEqual(0);
});
});
58 changes: 58 additions & 0 deletions spec/integration/ScoreCardSpec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
'use strict';

describe('ScoreCardIntegration', function () {
var card;

beforeEach(function () {
card = new ScoreCard();
});

describe('updateCard', function () {
beforeEach(function () {
card.card = [[]];
});
it('logs two new frames on card', function () {
card.updateCard(1);
card.updateCard(2);
card.updateCard(3);
expect(card.getCard()).toEqual([[1, 2], [3]]);
});
it('logs three new frames on card', function () {
card.updateCard(1);
card.updateCard(2);
card.updateCard(3);
card.updateCard(4);
card.updateCard(5);
expect(card.getCard()).toEqual([[1, 2], [3, 4], [5]]);
});
it('adds bonus to previous frame array on spare', function () {
card.updateCard(1);
card.updateCard(9);
card.updateCard(3);
expect(card.getCard()).toEqual([[1, 9, 3], [3]]);
});
it('does not add second roll as bonus to previous frame on spare', function () {
card.updateCard(1);
card.updateCard(9);
card.updateCard(3);
card.updateCard(5);
expect(card.getCard()).toEqual([[1, 9, 3], [3, 5]]);
});
it('adds both bonus rolls to previous frame array on strike', function () {
card.updateCard(1);
card.updateCard(3);
card.updateCard(10);
card.updateCard(0);
card.updateCard(2);
card.updateCard(4);
expect(card.getCard()).toEqual([[1, 3], [10, 0, 2, 4], [2, 4]]);
});
it('adds both bonus rolls to previous frame array on first frame strike', function () {
card.updateCard(10);
card.updateCard(0);
card.updateCard(2);
card.updateCard(4);
expect(card.getCard()).toEqual([[10, 0, 2, 4], [2, 4]]);
});
});
});
86 changes: 58 additions & 28 deletions spec/units/FrameSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,34 +8,28 @@ describe('Frame', function () {
});

describe('processRoll', function () {
it('calls checkFullFrame', function () {
spyOn(frame, 'checkFullFrame');
frame.processRoll();
expect(frame.checkFullFrame).toHaveBeenCalled();
beforeEach(function () {
var frame = new Frame();
});
it('calls updateFrameScore and passes roll() if rollcount is less than 2 and remainder greater than 0', function () {
spyOn(frame, 'getRollCount').and.returnValue(1);
spyOn(frame, 'remainder').and.returnValue(10);
spyOn(Math, 'random').and.returnValue(0.51);
it('calls updateFrameScore and passes roll() if isFullFrame and isStrike are both false', function () {
spyOn(frame, 'isFullFrame').and.returnValue(false);
spyOn(frame, 'isStrike').and.returnValue(false);
spyOn(frame, 'roll').and.returnValue(5);
spyOn(frame, 'updateFrameScore');
frame.processRoll();
expect(frame.updateFrameScore).toHaveBeenCalledWith(5);
});
it('calls updateFrameScore and passes 0 if rollcount is less than 2 but remainder is 0', function () {
spyOn(frame, 'getRollCount').and.returnValue(1);
spyOn(frame, 'remainder').and.returnValue(0);
it('calls updateFrameScore and passes 0 if first roll was strike', function () {
spyOn(frame, 'isFullFrame').and.returnValue(false);
spyOn(frame, 'isStrike').and.returnValue(true);
spyOn(frame, 'updateFrameScore');
frame.processRoll();
expect(frame.updateFrameScore).toHaveBeenCalledWith(0);
});
it('does not call updateFrameScore if rollcount is >= 2', function () {
spyOn(frame, 'getRollCount');
frame.getRollCount.and.returnValue(2);
spyOn(frame, 'remainder');
frame.remainder.and.returnValue(5);
spyOn(frame, 'updateFrameScore');
frame.processRoll();
expect(frame.updateFrameScore).not.toHaveBeenCalled();
it('throws error if frame is finished', function () {
spyOn(frame, 'isFullFrame').and.returnValue(true);
spyOn(frame, 'isStrike').and.returnValue(false);
expect(function () { frame.processRoll(); }).toThrow(new Error('ProcessRoll called on full frame'));
});
});

Expand All @@ -60,23 +54,23 @@ describe('Frame', function () {

describe('updateFrameScore', function () {
it('throws error if trying to update frame that already has two scores', function () {
spyOn(frame, 'getFrameScore').and.returnValue([2, 4]);
spyOn(frame, 'isFullFrame').and.returnValue(true);
expect(function () { frame.updateFrameScore(4); }).toThrowError();
});
it('throws error if passed a score that is not integer', function () {
spyOn(frame, 'getFrameScore').and.returnValue([2]);
expect(function () { frame.updateFrameScore(11); }).toThrowError(TypeError);
});
it('throws error if not passed a parameter', function () {
spyOn(frame, 'getFrameScore').and.returnValue([2]);
expect(function () { frame.updateFrameScore(); }).toThrowError(TypeError);
});
it('calls updateRollCount at the end', function () {
spyOn(frame, 'updateRollCount');
spyOn(frame, 'updateScoreCard');
frame.updateFrameScore(2);
expect(frame.updateRollCount).toHaveBeenCalled();
});
it('pushes new score to frameScore', function () {
spyOn(frame, 'updateScoreCard');
frame.updateFrameScore(2);
expect(frame.getFrameScore()).toEqual([2]);
});
Expand All @@ -98,17 +92,25 @@ describe('Frame', function () {
});
});

describe('checkFullFrame', function () {
it('calls updateIsFinished if rollCount is > 1', function () {
describe('isFullFrame', function () {
it('returns false if rollCount is < 2', function () {
spyOn(frame, 'getRollCount').and.returnValue(1);
expect(frame.isFullFrame()).toEqual(false);
});
it('returns true if rollCount is > 1', function () {
spyOn(frame, 'getRollCount').and.returnValue(2);
expect(frame.isFullFrame()).toEqual(true);
});
it('calls updateIsFinished with true if rollCount is > 1', function () {
spyOn(frame, 'getRollCount').and.returnValue(2);
spyOn(frame, 'updateIsFinished');
frame.checkFullFrame();
frame.isFullFrame();
expect(frame.updateIsFinished).toHaveBeenCalledWith(true);
});
it('does not call updateIsFinished if rollCount is < 2', function () {
spyOn(frame, 'getRollCount').and.returnValue(1);
spyOn(frame, 'updateIsFinished');
frame.checkFullFrame();
frame.isFullFrame();
expect(frame.updateIsFinished).not.toHaveBeenCalled();
});
});
Expand Down Expand Up @@ -138,11 +140,28 @@ describe('Frame', function () {
it('pushes latest frameScore to scoreCard', function () {
var card = { updateCard: function (score) {} };
spyOn(frame, 'getScoreCard').and.returnValue(card);
spyOn(frame, 'getFrameScore').and.returnValue([5]);
spyOn(frame, 'getLastRoll').and.returnValue(5);
spyOn(card, 'updateCard');
frame.updateScoreCard();
expect(frame.getScoreCard).toHaveBeenCalled();
expect(frame.getLastRoll).toHaveBeenCalled();
expect(card.updateCard).toHaveBeenCalledWith(5);
});
it('calls getLastRoll', function () {
var card = { updateCard: function (score) {} };
spyOn(frame, 'getScoreCard').and.returnValue(card);
spyOn(frame, 'getLastRoll').and.returnValue(5);
spyOn(card, 'updateCard');
frame.updateScoreCard();
expect(frame.getLastRoll).toHaveBeenCalled();
});
it('calls getScoreCard', function () {
var card = { updateCard: function (score) {} };
spyOn(frame, 'getScoreCard').and.returnValue(card);
spyOn(frame, 'getLastRoll').and.returnValue(5);
spyOn(card, 'updateCard');
frame.updateScoreCard();
expect(frame.getScoreCard).toHaveBeenCalled();
expect(card.updateCard).toHaveBeenCalledWith([5]);
});
});

Expand All @@ -152,4 +171,15 @@ describe('Frame', function () {
expect(frame.getFrameScore()).toEqual([5, 3]);
});
});

describe('getLastRoll', function () {
it('returns int of last element in frame', function () {
spyOn(frame, 'getFrameScore').and.returnValue([2, 3]);
expect(frame.getLastRoll()).toEqual(3);
});
it('returns int of last element in frame when only one', function () {
spyOn(frame, 'getFrameScore').and.returnValue([2]);
expect(frame.getLastRoll()).toEqual(2);
});
});
});
51 changes: 50 additions & 1 deletion spec/units/GameSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ describe('Game', function () {
expect(frame.processRoll).toHaveBeenCalled();
});
it('calls nextFrame', function () {
var frame = { processRoll: function () {} };
spyOn(game, 'getCurrentFrame').and.returnValue(frame);
spyOn(game, 'nextFrame');
game.play();
expect(game.nextFrame).toHaveBeenCalled();
Expand Down Expand Up @@ -62,10 +64,57 @@ describe('Game', function () {
});
});

describe('getTotalScore', function () {
it('calculates and return total score', function () {
var card = { getCard: function () { return [[1, 2], [5, 2]]; } };
spyOn(game, 'getScoreCard').and.returnValue(card);
expect(game.getTotalScore()).toEqual(10);
});
});

describe('getScoreCard', function () {
it('returns a frame object', function () {
it('returns a ScoreCard object', function () {
var card = game.getScoreCard();
expect(card instanceof ScoreCard).toBeTruthy();
});
});

describe('flatten', function () {
it('returns a flattened array', function () {
var array = [[1, 2], [5, 2]];
expect(flatten(array)).toEqual([1, 2, 5, 2]);
});
it('returns a flattened array', function () {
var array = [[0]];
expect(flatten(array)).toEqual([0]);
});
it('returns a flattened array', function () {
var array = [[0, 0]];
expect(flatten(array)).toEqual([0, 0]);
});
it('throws TypeError if not passed an array', function () {
expect(function () { flatten(1); }).toThrow(new TypeError('Passed: 1'));
});
it('returns a empty flat array if passed [[]]', function () {
var array = [[]];
expect(flatten(array)).toEqual([]);
});
});

describe('sumArray', function () {
it('returns sum of a flat array', function () {
var array = [1, 2, 5, 2];
expect(sumArray(array)).toEqual(10);
});
it('can take array with 0', function () {
expect(sumArray([0])).toEqual(0);
});
it('throws TypeError if not passed an array', function () {
expect(function () { sumArray(1); }).toThrow(new TypeError('Passed: 1'));
});
it('returns 0 if array is empty', function () {
var array = [];
expect(sumArray(array)).toEqual(0);
});
});
});
Loading

0 comments on commit 7cde9e6

Please sign in to comment.