I am new to Node.js. I was trying to write a jest unit test cases for AWS lambda function(for node environment). I used a node module called "lambda-tester" to test it. But the problem with "lambda-tester" is, it will hit the actual service and return the data. I don't want to do that. I need to mock the service call.
So, I wanted to go with the plain old way. But, I have issues with mocking it. Can you help me to write basic unit test case for the below lambda ith mocking the function "serviceFunction" ?
const dataService = require('../dataService');
exports.lambdaService = async event => {
let response = await serviceFunction(event.id);
if (response.code == 200) {
return response;
} else {
return {
statusCode: response.code,
body: JSON.stringify({
message: response.message
})
};
}
};
const serviceFunction = async id => {
return await dataService.retrieveData(id);
};
You can use jest.spyOn(object, methodName, accessType?) method to mock dataService.retrieveData
method. And, your serviceFunction
function only has one statement, so you can test lambdaService
function with it together.
E.g.
index.js
:
const dataService = require('./dataService');
exports.lambdaService = async event => {
let response = await serviceFunction(event.id);
if (response.code == 200) {
return response;
} else {
return {
statusCode: response.code,
body: JSON.stringify({
message: response.message
})
};
}
};
const serviceFunction = async id => {
return await dataService.retrieveData(id);
};
dataService.js
:
module.exports = {
retrieveData: async id => {
return { code: 200, data: 'real data' };
}
};
index.spec.js
:
const { lambdaService } = require('.');
const dataService = require('./dataService');
describe('lambdaService', () => {
beforeEach(() => {
jest.restoreAllMocks();
});
test('should return data', async () => {
const mResponse = { code: 200, data: 'mocked data' };
const mEvent = { id: 1 };
const retrieveDataSpy = jest.spyOn(dataService, 'retrieveData').mockResolvedValueOnce(mResponse);
const actualValue = await lambdaService(mEvent);
expect(actualValue).toEqual(mResponse);
expect(retrieveDataSpy).toBeCalledWith(mEvent.id);
});
test('should return error message', async () => {
const mResponse = { code: 500, message: 'Internal server error' };
const mEvent = { id: 1 };
const retrieveDataSpy = jest.spyOn(dataService, 'retrieveData').mockResolvedValueOnce(mResponse);
const actualValue = await lambdaService(mEvent);
expect(actualValue).toEqual({ statusCode: 500, body: JSON.stringify({ message: mResponse.message }) });
expect(retrieveDataSpy).toBeCalledWith(mEvent.id);
});
test('should throw an error', async () => {
const mEvent = { id: 1 };
const retrieveDataSpy = jest.spyOn(dataService, 'retrieveData').mockRejectedValueOnce(new Error('network error'));
await expect(lambdaService(mEvent)).rejects.toThrowError(new Error('network error'));
expect(retrieveDataSpy).toBeCalledWith(mEvent.id);
});
});
Unit test result with coverage report:
PASS src/stackoverflow/58623194/index.spec.js
lambdaService
✓ should return data (6ms)
✓ should return error message (4ms)
✓ should throw an error (2ms)
----------------|----------|----------|----------|----------|-------------------|
File | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s |
----------------|----------|----------|----------|----------|-------------------|
All files | 90 | 100 | 66.67 | 90 | |
dataService.js | 50 | 100 | 0 | 50 | 3 |
index.js | 100 | 100 | 100 | 100 | |
----------------|----------|----------|----------|----------|-------------------|
Test Suites: 1 passed, 1 total
Tests: 3 passed, 3 total
Snapshots: 0 total
Time: 4.619s
Source code: https://github.com/mrdulin/jest-codelab/tree/master/src/stackoverflow/58623194
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With