This is example has extracted from this boilerplate.
Custom middleware:
export default function clientMiddleware() {
return ({dispatch, getState}) => {
return next => action => {
if (typeof action === 'function') {
return action(dispatch, getState);
}
const { promise, types, ...rest } = action; // eslint-disable-line no-redeclare
if (!promise) {
return next(action);
}
const [REQUEST, SUCCESS, FAILURE] = types;
next({...rest, type: REQUEST});
const client = new ApiClient();
const actionPromise = promise(client);
actionPromise.then(
(result) => next({...rest, result, type: SUCCESS}),
(error) => next({...rest, error, type: FAILURE})
).catch((error)=> {
console.error('MIDDLEWARE ERROR:', error);
next({...rest, error, type: FAILURE});
});
return actionPromise;
};
};
}
Wrapping Superagent
library for API call:
import superagent from 'superagent';
import config from '../config';
const methods = ['get', 'post', 'put', 'patch', 'del'];
function formatUrl(path) {
const adjustedPath = path[0] !== '/' ? '/' + path : path;
return adjustedPath;
}
export default class ApiClient {
constructor(req) {
methods.forEach((method) =>
this[method] = (path, { params, data } = {}) => new Promise((resolve, reject) => {
const request = superagent[method](formatUrl(path));
if (params) {
request.query(params);
}
if (data) {
request.send(data);
}
request.end((err, { body } = {}) => err ? reject(body || err) : resolve(body));
}));
}
empty() {}
}