Skip to content

Commit

Permalink
Merge pull request #1 from davidcostadev/feature/add_tests
Browse files Browse the repository at this point in the history
Add tests on api and middleware files
  • Loading branch information
lucianoratamero committed Jul 18, 2019
2 parents 2397103 + c9725a8 commit a0063ff
Show file tree
Hide file tree
Showing 5 changed files with 235 additions and 2 deletions.
8 changes: 8 additions & 0 deletions .babelrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"presets": ["@babel/preset-env"],
"env": {
"test": {
"plugins": ["@babel/plugin-transform-runtime"]
}
}
}
48 changes: 48 additions & 0 deletions api.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
import { fetchFromApi } from './api';

describe('fetchFromApi', () => {
beforeEach(() => {
fetch.resetMocks();
});

it('should resolve fetch and return data with error', async () => {
fetch.mockResolvedValue({
status: 400,
message: 'The name is empty'
});

const header = {
method: 'POST',
body: { name: '' }
};
try {
await fetchFromApi('http://localhost:3000/products');
} catch (e) {
expect(e).toEqual({
status: 400,
message: 'The name is empty'
});
}
});

it('should resolve fetch and return data', async () => {
fetch.mockResolvedValue({
data: [{ name: 'Xbox' }]
});

const response = await fetchFromApi('http://localhost:3000/products');

expect(response).toEqual({
data: [{ name: 'Xbox' }]
});
});

it('should reject fetch and catch by error', async () => {
fetch.mockRejectedValue(new Error('404 Not found'));
try {
await fetchFromApi('http://localhost:3000/products/999');
} catch (e) {
expect(e).toEqual(new Error('404 Not found'));
}
});
});
162 changes: 162 additions & 0 deletions middleware.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,162 @@
import { apiMiddleware } from './middleware';

describe('apiMiddleware', () => {
it('Should dispatch action success and return the data body', async () => {
const dispatch = jest.fn();
const getState = jest.fn();
const next = jest.fn();

function get() {
return 'application/json';
}

const body = {
data: [{ id: 1, name: 'Xbox' }]
};

function json() {
return Promise.resolve(body);
}

const apiCallFunction = jest.fn().mockResolvedValue({
headers: {
get
},
json
});

const action = {
types: {
request: 'REQUEST',
success: 'SUCCESS',
failure: 'FAILURE'
},
apiCallFunction
};

const response = await apiMiddleware({ dispatch, getState })(next)(action);

expect(next).not.toBeCalled();
expect(getState).toBeCalled();

const expectedResponse = {
data: body,
headers: {
get
},
json
};
expect(dispatch).toBeCalledWith({
extraData: {},
type: 'REQUEST'
});
expect(dispatch).toBeCalledWith({
extraData: {},
response: expectedResponse,
type: 'SUCCESS'
});
expect(response).toEqual(expectedResponse);
});

it('Should dispatch action failture when has some error on request', async () => {
const dispatch = jest.fn();
const getState = jest.fn();
const next = jest.fn();

function get() {
return 'application/json';
}

const body = {
status: 500,
message: 'Internal Error'
};

function json() {
return Promise.resolve(body);
}

const apiCallFunction = jest.fn().mockRejectedValue({
headers: {
get
},
json
});

const action = {
types: {
request: 'REQUEST',
success: 'SUCCESS',
failure: 'FAILURE'
},
apiCallFunction
};

const expectedResponse = {
data: body,
headers: {
get
},
json
};

try {
await apiMiddleware({ dispatch, getState })(next)(action);
} catch (error) {
expect(error).toEqual(expectedResponse);
}

expect(next).not.toBeCalled();
expect(getState).toBeCalled();
expect(dispatch).toBeCalledWith({
extraData: {},
type: 'REQUEST'
});
expect(dispatch).toBeCalledWith({
extraData: {},
response: expectedResponse,
error: expectedResponse,
type: 'FAILURE'
});
});

it("Should catch error when it doesn't pass all types actions", async () => {
const dispatch = jest.fn();
const getState = jest.fn();
const next = jest.fn();
const action = {
types: {}
};

try {
await apiMiddleware({ dispatch, getState })(next)(action);
} catch (error) {
expect(error).toEqual(
new Error(
'Expected action.types to be an object/dict with three keys (request, success and failure), and the values should be strings.'
)
);
}
});

it('Should catch error when apiCallFunction dependency is not a function', async () => {
const dispatch = jest.fn();
const getState = jest.fn();
const next = jest.fn();
const action = {
types: {
request: 'REQUEST',
success: 'SUCCESS',
failure: 'FAILURE'
}
};

try {
await apiMiddleware({ dispatch, getState })(next)(action);
} catch (error) {
expect(error).toEqual(
new Error('Expected `apiCallFunction` to be a function.')
);
}
});
});
18 changes: 16 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"description": "Middleware and helpers to improve the React-Redux flow when communicating with APIs.",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\""
"test": "jest *.test.js"
},
"repository": {
"type": "git",
Expand All @@ -22,5 +22,19 @@
"bugs": {
"url": "https://github.com/labcodes/react-redux-api-tools/issues"
},
"homepage": "https://github.com/labcodes/react-redux-api-tools#readme"
"homepage": "https://github.com/labcodes/react-redux-api-tools#readme",
"devDependencies": {
"@babel/core": "^7.5.4",
"@babel/plugin-transform-runtime": "^7.5.0",
"@babel/preset-env": "^7.5.4",
"@babel/runtime": "^7.5.4",
"jest": "^24.8.0",
"jest-fetch-mock": "^2.1.2"
},
"jest": {
"automock": false,
"setupFiles": [
"<rootDir>/setupJest.js"
]
}
}
1 change: 1 addition & 0 deletions setupJest.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
global.fetch = require('jest-fetch-mock');

0 comments on commit a0063ff

Please sign in to comment.