Home > Software engineering >  My mapStateToProps is returning a function instead of an array
My mapStateToProps is returning a function instead of an array

Time:11-04

I created a reducer, action creator and a mapStateToProps. when I log the state from the mapStateToProps, it logs the expected data but when I log it in the props, it returns a function like template. I dont know qwhat is happening there.

I need help, please.

Reducer

import { FETCH_PRODUCTS } from '../action/types';

const init = [];
const productsReducer = (state = init, action) => {
  switch (action.type) {
    case FETCH_PRODUCTS:
      return action.payload;

    default:
      return state;
  }
};

export default productsReducer;

Action Creator

export const fetchProducts = () => async (dispatch) => {
  const { data } = await apiData(products);

  dispatch({
    type: FETCH_PRODUCTS,
    payload: data.categories,
  });
};

Component where I am mapping to props

import React, { Component } from 'react';
import { connect } from 'react-redux';

import { fetchCategories, fetchProducts } from '../../../redux/action/actionCreators';
import './women.css';

class All extends Component {
  componentDidMount() {
    this.props.categories();
    this.props.products();
  }

  render() {
    console.log(this.props.products);
    return (<div>Hell0</div>);
  }
}

const mapStateToProps = (state) => { 
  // console.log(state);
   return { products: state.products }
  };

export default connect(mapStateToProps,
  {
    categories: fetchCategories,
    products: fetchProducts,
  })(All);

Result I get

ƒ () {
        return dispatch(actionCreator(...arguments));
      }

Instead of array

I have tried calling the products as a function by adding parenthesis to the end something like

console.log(this.props.products());

but it returns pending promise and runs infinetely.

CodePudding user response:

This is because your name of state and action creator is the same and the action creator is over-writing your state variable in props.

const mapStateToProps = (state) => { 
  return { 
    // this.props.products -> state
    products: state.products 
  }
};

export default connect(mapStateToProps, {
  categories: fetchCategories,

  // this.props.products -> action creator
  products: fetchProducts,
})(All);

You will have to rename either your action creator or your state variable name. I would say, keep the fetch prefix for the action creators so that it is very clear that it will fetch items from server.

const mapStateToProps = (state) => { 
  // console.log(state);
  return { products: state.products }
};

export default connect(mapStateToProps, {
  fetchCategories,
  fetchProducts,
})(All);

Then, in your componentDidMount, you can update the function names:

componentDidMount() {
  this.props.fetchCategories();
  this.props.fetchProducts();
}
  • Related