How We Saved a Week of Dev Time Building a React-Redux Application

Wildebeest
4 min readFeb 8, 2017

In our growing shop, projects keep getting bigger and deadlines shorter. Searching for and freeing up bottlenecks in the development process has become critical to our projects’ successes.

One common area where bottlenecks occur are in retrieving responses from an API for the front-end application while the API is still under development. We noticed that at the end of some sprints, our front-end developers were consistently leaving notes about how the process could have been improved:

We had to hard code mock data in the components for the first part of the dev process until the API was up. Then we had to change the code so that it used the API responses when the API was ready.

We couldn’t effectively test API calls and handling responses until the API was ready.

The API was up and down throughout the sprint.

Simply put, the effects of roadblocks on the back-end should be minimized for the front-end. One thing that greatly helps reduce the dependency on the back-end dev team is creating a mock API to return responses in lieu of the API that is under construction.

In a recent project, using this technique saved our front-end developers upwards of 40-hours over other projects of similar scale. Some benefits we’ve found for implementing the mock API in the initial stages of development are:

  • Consistent behavior, no unexpected downtime
  • Fully simulates an API request/response so you can build your app without having to refactor later
  • Easy to remove once the API is built and deployed
  • Easily create numerous dynamic success and error responses with some creativity

In a React/Redux application, we create the connect components and containers from the get-go. However, if our application relied on data fetched from an API via Redux actions and the API endpoints were not built yet, we would not being able to make substantive API calls.

Also while the API is being built out, our mock API handles all requests and responses. This utility emulates the existence of a real API and is easily removed from the codebase without much/any modification of the actions/reducers and containers/components.

For our HTTP client, we like to use axios, a promise-based client for browser and Node.js. For creating mock API responses, we prefer axios-mock-adapter. It acts as a middleware which can intercept requests from axios and return preset data.

We keep the mock API in its own utility file separate from the initialization of client. Here is a sample set up that would return 10 posts when the axios client makes a get request to /posts . We import the different mock responses from another file to keep this one less cluttered and separate concerns.

mockAPI utility file:

import MockAdapter from 'axios-mock-adapter';
// Utility library, documentation at: lodash.com/docs/
import { times, sample } from 'lodash';
import { postActive, postPending, postHidden } from './mockResponses';
export default function initializeMockAPI(client) {
const mock = new MockAdapter(client);
// `config` is the axios config and contains things like the url
mock.onGet().reply((config) => {
const slugs = config.url.split('/');

// List 10 Posts
// Randomly sample between active, pending, and hidden
if (slugs.length === 1 && slugs[0] === 'posts') {
return [200, {
data: times(10, () =>
sample([ postActive(), postPending(), postHidden()])),
}];
}
// Post Detail
if (slugs.length === 2 && slugs[0] === 'posts') {
return [200, (() => {
if (slugs[1] < 500) {
return postActive(slugs[1]);
} else if (slugs[1] < 1001) {
return postPending(slugs[1]);
}
return postHidden(slugs[1]);
})()];
}
// If no matches, return a 404.
return [404];
});
return mock;
}

mockResponses utility file:

I added in ES6 default parameters for the id in each function, so that if you were to have post detail pages that had different UI for active, pending, or hidden, they can be differentiated within the mock API via the id.

import { random } from 'lodash';// Provide a random id between 100 and 500 if one isn't provided
export const activePost = (id = random(100,500)) => {
return {
id,
status: active,
title: 'Active Post Title',
body: 'Active Post Body',
};
};
export const pendingPost = (id = random(501, 1000)) => {
return {
id,
status: pending,
title: 'Pending Post Title',
body: 'Pending Post Body',
};
};
export const hiddenPost = (id = random(1001, 1500)) => {
return {
id,
status: hidden,
title: 'Hidden Post Title',
body: 'Hidden Post Body',
};
};

Where you run the initializeMockAPI function will vary depending on where the client is initialize if you have a client/promise middleware utility. Wherever you initialize axios, run initializeMockAPI(client), passing in the initialized client. Now when you make API calls to /posts or /posts/:id , you will get back a response from the mock API. When the API is ready to plug into your application, simple remove the function that initializes the mock API.

When building out a front-end and API at the same time, spending a little bit of time to set up a mock API while waiting for the development of the API can save your team time on refactoring. With a mock API in place, your front-end developers can build out the front end with consistent API requests and responses. Removing the mock API when the real API is ready is as simple as removing one line of code.

This article was contributed by Yo Wakita, a Full Stack Developer at Wildebeest.

--

--

Wildebeest

A product studio in LA that builds custom software for brands.