Testing NodeJS API with Mocha and Chai
Published: 2023-07-22 11:52:58

While working on a big project, It's also very necessary to check the written API should work well while making the app or while making some changes later on. Writing test cases allow us easily track if any error occurs in any instance.

 

In this tutorial, We will learn to write test cases for Node.js Restful API using Mocha and Chai. We will mainly test a Get API and a POST API to have a basic understanding of how to start writing test cases. If you want to know about the very basics of testing in Nodejs and about the Mocha and Chai, then you can read my recently posted article about the Basics about Writing Tests in Nodejs API Application


### Let's Get Started


### Create Node.js App
Create a project folder and move to it.

``````mkdir test-with-mocha && cd test-with-mocha/``````

Create package.json file with NPM command

``````npm init --yes``````

Above command will create package.json file with default values

Install needed NPM package

``````npm install express``````

Now install dev dependencies

``````npm install mocha chai chai-http faker --save-dev``````

**Mocha:** Mocha is a javascript framework for Node.js which allows Asynchronous testing.

**Chai:** Chai is a BDD / TDD assertion library for **node** and the browser that can be delightfully paired with any javascript testing framework.

**chai-http:** Chai HTTP provides an interface for live integration testing via superagent.

**faker:** It is useful for creating dummy data while making HTTP requests.

 


### Server File(app.js)

``````//Load express module
const express = require('express'),
app = express(),
bodyParser = require("body-parser"),
faker = require('faker');
 
 
app.use(bodyParser.json());
 
//Define request response in root URL (/)
app.get('/', (req, res)=> {
  res.send('App running successfully!');
})
 
// Create a basic get API with some response...
app.get('/post-list', (req,res)=>{
  if(!req.query.user_id || req.query.user_id==""){
    res.status(401).send({"message":"User Id parameter is missing"})
  }
  else{
    res.json({
      "userId": 1,
      "id": 1,
      "title": "sunt aut facere repellat provident occaecati excepturi optio reprehenderit",
      "body": "quia et suscipit suscipit recusandae consequuntur expedita et cum reprehenderit molestiae ut ut quas totam nostrum rerum est autem sunt rem eveniet architecto"
    })
  }
 
})
 
// Dummy post API with some input params and response.
app.post('/submit-data', (req,res)=>{
  if(!req.body.name || !req.body.email){
    res.status(401).json({
      message : "Mandatory params are missing!"
    })
  }
  else{
    res.status(200).json({
      message : "data saved successfully"
    })
  }
})
 
//Launch listening server on port 8080
app.listen(4000, ()=> {
  console.log('App listening on port 4000!')
})
 
module.exports = app;``````


### Start writing Tests with Mocha and Chai


At first add below line in package.json file for testing purpose.

``````"test": "./node_modules/.bin/mocha test --timeout 0 --exit"``````

Create a test file named index.js inside newly created folder named test.

 

Write a simple test case to check if the server is running properly. 

``````const chai = require('chai'),
chaiHttp = require('chai-http'),
server = require('../app'),
faker = require('faker'),
should = chai.should();
 
chai.use(chaiHttp);
 
describe('Init', function () {
 
it('check app status', function (done) {
  chai.request(server).get('/').end((err, res) => {
    should.not.exist(err);
    res.should.have.status(200);
    done();
  })
});
 
});``````

Now run the test with command **npm test.**


![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/pslwfohpr35jp4dvc1t7.png)

**Test Cases for get API**

 

Now let's move to test get API with its different cases.

``````describe('/Get API test', function () {
 
  it('Check the api without user id parameter', function (done) {
    chai.request(server).get('/post-list').end((err, res) => {
      should.not.exist(err);
      res.should.have.status(401);
      res.body.should.be.a('object');
      res.body.should.have.property('message');
      res.body.should.have.property('message').eql('User Id parameter is missing');
      done();
    })
  });
 
  it('Check the api with user id. Success', function (done) {
    chai.request(server).get('/post-list?user_id=1').end((err, res) => {
      should.not.exist(err);
      res.should.have.status(200);
      res.body.should.be.a('object');
      res.body.should.have.property('userId');
      res.body.should.have.property('title');
      res.body.should.have.property('body');
      done();
    })
  });
 
});``````

In the above code, we have tested two cases, the first case is to test on hitting API without parameter and the second is with valid parameter to get success response. There may other cases but for simplicity, I have written only two cases now.

after running **npm test** below outcome will be there on the terminal


![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/7l7a1n6ouwn9azdcf8mc.png)

Now since we have total of 3 test cases, So it's showing 3 passing and also we can see the name of cases passed.

 

**Test Case for Post API**

``````describe('/POST API test', function () {
 
  it('Check the api without parameters . failure case', function (done) {
    chai.request(server).post('/submit-data').send({}).end((err, res) => {
      should.not.exist(err);
      res.should.have.status(401);
      res.body.should.be.a('object');
      res.body.should.have.property('message');
      res.body.should.have.property('message').eql('Mandatory params are missing!');
      done();
    })
  });
 
  it('Check the API with valid parameters. Success', function (done) { 
    chai.request(server).post('/submit-data').send({name:faker.name.firstName(),email:faker.internet.email()}).end((err, res) => { 
      should.not.exist(err);
      res.should.have.status(200);
      res.body.should.be.a('object');
      res.body.should.have.property('message');
      res.body.should.have.property('message').eql('data saved successfully');
      done();
    })
  });
 
});``````

Here we have tested two cases of post API, which can be many more. One if failure case and other is success case, I have used here faker for creating dummy data while making the HTTP request. 

After running npm test command on terminal we will get like below:


![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9knqniscqywk0101vl0g.png)

Great, our tests are all positive and we have now good understanding to start writing test cases for live application.

 

**Complete test file(test/index.js)**

``````const chai = require('chai'),
chaiHttp = require('chai-http'),
server = require('../app'),
faker = require('faker'),
should = chai.should();
 
chai.use(chaiHttp);
 
describe('Init', function () {
 
  it('check app status', function (done) {
    chai.request(server).get('/').end((err, res) => {
      should.not.exist(err);
      res.should.have.status(200);
      done();
    })
  });
 
});
 
// Test a get route...
 
describe('/Get API test', function () {
 
  it('Check the api without user id parameter', function (done) {
    chai.request(server).get('/post-list').end((err, res) => {
      should.not.exist(err);
      res.should.have.status(401);
      res.body.should.be.a('object');
      res.body.should.have.property('message');
      res.body.should.have.property('message').eql('User Id parameter is missing');
      done();
    })
  });
 
  it('Check the api with user id. Success', function (done) {
    chai.request(server).get('/post-list?user_id=1').end((err, res) => {
      should.not.exist(err);
      res.should.have.status(200);
      res.body.should.be.a('object');
      res.body.should.have.property('userId');
      res.body.should.have.property('title');
      res.body.should.have.property('body');
      done();
    })
  });
 
});
 
describe('/POST API test', function () {
 
  it('Check the api without parameters . failure case', function (done) {
    chai.request(server).post('/submit-data').send({}).end((err, res) => {
      should.not.exist(err);
      res.should.have.status(401);
      res.body.should.be.a('object');
      res.body.should.have.property('message');
      res.body.should.have.property('message').eql('Mandatory params are missing!');
      done();
    })
  });
 
  it('Check the API with valid parameters. Success', function (done) {
    chai.request(server).post('/submit-data').send({ 
      name: faker.name.firstName(),
      email: faker.internet.email()
    }).end((err, res) => {
      should.not.exist(err);
      res.should.have.status(200);
      res.body.should.be.a('object');
      res.body.should.have.property('message');
      res.body.should.have.property('message').eql('data saved successfully');
      done();
    })
  });
 
});``````


### Conclusion

In this article, we learned about how to start writing test cases for Node.js Restful API. So writing test cases for Nodejs Restful API is not very difficult.

If you are new to Node.js then find Nodejs Sample Application to start the app for enterprise-level application.

Let me know your thoughts over email **demo.jsonworld@gmail.com.** I would love to hear them and If you like this article, share with your friends.

 

Thank You!
This article is originally posted over [jsonworld](jsonworld.com)