Plebeian
Plebeian

Reputation: 13

Fetching data with redux actions

I am having an issue internally with how to structure my redux actions that fetch data via a rest api.

I am fetching a variety of data like

I am wondering if I create an action that fetch's the data from each endpoint or if I create a singular fetch action that fetches the data from a supplied route?

Current Implementation:

function requestPosts(site) {
return {
    type: REQUEST_POSTS,
    site
}

function fetchPosts(site) {
return dispatch => {
    dispatch(requestPosts(site))
    return fetch(`http://notareallink.com/posts`)
        .then( response => response.json() )
        .then( json => dispatch( receivePosts( site, json ) ) )
}

function requestPost(site) {
return {
    type: REQUEST_POST,
    site
}

function fetchPost(site) {
return dispatch => {
    dispatch(requestPost(site))
    return fetch(`http://notareallink.com/post/post-id`)
        .then( response => response.json() )
        .then( json => dispatch( receivePost( site, json ) ) )
}

function requestUsers(site) {
return {
    type: REQUEST_USERS,
    site
}

function fetchUsers(site) {
return dispatch => {
    dispatch(requestUsers(site))
    return fetch(`http://notareallink.com/users`)
        .then( response => response.json() )
        .then( json => dispatch( receiveUsers( site, json ) ) )
}

To me this feels like a load of duplicate code basically doing the same thing (Fetching the data from the endpoint).

Is this the correct way to do it or should I be creating a singular action that does the data fetch and pass it the relevant route?

I am sorry if this is not very clear but I am trying to wrap my head around this as I type this out.

Upvotes: 1

Views: 2278

Answers (1)

Yury Tarabanko
Yury Tarabanko

Reputation: 45106

All of this is just functions that can call another functions to handle repetative tasks w/o code duplication.

First of all you need to extract repetative fetch calls.

const callAPI = url => fetch(`http://notareallink.com/${url}`).then(res => res.json())

To avoid repetative action dispatching you can use middlewares. It seems you already have thunk middleware. You can add your own or use a package.

const promiseMiddleware = ({dispatch}) => next => action => {
   const {promise, pending, success, fail} = action
   if(promise) {
     dispatch(pending());
     promise.then(
       res => dispatch(success(res)),
       err => dispatch(fail(err))
     )
   }
   return next(action)
}

And use it like this

const requestPosts = () => ({ type: REQUEST_POSTS })
const recievePosts = posts => ({ type: RECIEVE_POSTS, posts })
const requestPostsFail = reason => ({ type: REQUEST_POSTS_FAIL, reason })

const fetchPosts = () => dispatch => dispatch({
  promise: callAPI('posts'),
  pending: requestPosts,
  success: receivePosts,
  fail: requestPostsFail
})

Upvotes: 1

Related Questions