Running a Test with Multiple Test Cases in Jasmine

Running a Test with Multiple Test Cases in Jasmine

javascript Mar 27, 2018

If you have previously used testing frameworks such as NUnit or JUnit, you would know there's the ability to run one test with a number of different test cases by simply decorating your test with the test cases. An example from NUnit Documentation is:

[TestCase(12,3,4)]
[TestCase(12,2,6)]
[TestCase(12,4,3)]
public void DivideTest(int n, int d, int q)
{
  Assert.AreEqual( q, n / d );
}

At work, I've been doing a lot of unit testing of our Angular 4 project using Jasmine. I've found the need to run a singular test multiple times with different test cases just like in the above example. However, to my knowledge, there's no functionality that comes with Jasmine to easily do this.

The initial way I ran test cases was through creating an array of test cases within my it function like this:

describe('divideTest', () => {
    it('should divide correctly', () => {
        const testCases = [
            { n: 12, d: 3, q: 4 },
            { n: 12, d: 2, q: 6 },
            { n: 12, d: 4, q: 5 } // Will fail!
        ];
        
        testCases.forEach(test => {
            expect(n / d).toEqual(q);
        });
    });
});

This worked fine and will run all test cases. However, it runs all test cases in the one function and if a test case fails, Jasmine will not notify us exactly what exactly case failed. We can see the third test case will obviously fail in this case ({ n: 12, d: 4, q: 3 }), Jasmine will show the error as:
Screen-Shot-2018-03-27-at-3.34.58-pm

We can see the test failed, but we can only see it expected a result of 3 to be 5. From looking at this alone, I'd have no idea what caused the actual failure. To see which test case it actually was, we'd have to scan through each case and see which case matches. For a small amount of simple test cases, this shouldn't be a problem (like in this example). But when you are constructing tests around more complex functions, it will be much harder to find the test case that failed.

What you can do is create more descriptive test cases by simply moving the forEach loop outside of the it statement like so:

describe("divideTest", function () {
  const testCases = [
    { n: 12, d: 3, q: 4 },
    { n: 12, d: 2, q: 6 },
    { n: 12, d: 4, q: 5 }
  ];

  testCases.forEach(test => {
    it(`should divide ${test.n} by ${test.d} correctly`, () => {
      expect(test.n / test.d).toEqual(test.q);
    });
  });
});

You'll notice that I made the should description more verbose. This makes it easy to understand which case failed and will output:
Screen-Shot-2018-03-27-at-3.40.34-pm

Now we can easily see which test case resulted in a failure. You can also go further by specifying the index of the test case you are running like this:

describe("divideTest", function () {
  const testCases = [
    { n: 12, d: 3, q: 4 },
    { n: 12, d: 2, q: 6 },
    { n: 12, d: 4, q: 5 }
  ];

  testCases.forEach((test, index) => {
    it(`should divide ${test.n} by ${test.d} correctly (testcase: ${index + 1})`, () => {
      expect(test.n / test.d).toEqual(test.q);
    });
  });
});

The verbosity of your test case is ultimately up to you and you should customise it to your needs.

Hope this helps you make more easy to read tests using Jasmine!

Update (24/08/2019): Check out /running-a-test-with-multiple-test-cases-using-jest-enzyme-react/ for a Jest/Enzyme/React version of this article.

Tags

Harvey Delaney

Front End Engineer II at Amazon Web Services

Exclusive Usenet provider deals

Harvey's essential software engineering books

1

The Pragmatic Programmer: From Journeyman to Master

2

Clean Code: A Handbook of Agile Software Craftsmanship

3

Code Complete: A Practical Handbook of Software Construction

4

Design Patterns: Elements of Reusable Object-Oriented Software

Harvey is a participant in the Amazon Services LLC Associates Program, an affiliate advertising program designed to provide a means for sites to earn advertising fees by advertising and linking to amazon.com
Great! You've successfully subscribed.
Great! Next, complete checkout for full access.
Welcome back! You've successfully signed in.
Success! Your account is fully activated, you now have access to all content.