learningMonk
learningMonk

Reputation: 1401

not able to add items to cart from product page using react redux

I have listed out some products in product list page. I am not able to add product in my cart. It is showing error in my reducer code. Here is my code.

action

  export const addToCart = id => ({
    type: ADD_TO_CART,
    id
  });

reducer code

const initialState = {
    products: [
      {
        id: 1,
        title: "Dell Inspiron 3581",
        discount: 10,
        price: 110,
        img: Image1,
      },
      {
        id: 2,
        title: "Dell Vostro 3362",
        discount: 10,
        price: 80,
        img: Image2,
      },
      { id: 3, title: "Acer TravelMate", discount: 0, price: 120, img: Image3 },
      {
        id: 4,
        title: "Lenovo ideapad core",
        discount: 15,
        price: 260,
        img: Image4,
      },
      { id: 5, title: "Lenovo V145", discount: 0, price: 160, img: Image5 },
      {
        id: 6,
        title: "Asus Zephyrus G14",
        discount: 5,
        price: 90,
        img: Image6,
      },
    ],
    filteredProducts: [],
    cartItems: [],
    total: 0,
    cartCount: 0,
  };
  
export default function productReducer(state = initialState, action){
     switch(action.type){
      
       case ADD_TO_CART:
      const { cartItems, products, cartCount,total } = state;

      let productToAdd = cartItems.find(item=>item.id===action.id);
      let count;
      if (!productToAdd) {
        productToAdd = products.find(obj => obj.id === action.id);
        count = 1;
      } else {
        count = productToAdd.count + 1;
      }
      const pid = productToAdd.id;
      const newCart = { ...state.cartItems, [pid]: { ...productToAdd, count } };
      const newcount = cartCount + 1; 
      const newTotal = total+productToAdd.price
      return { ...state, cartItems: newCart, cartCount: newcount,total:newTotal};

        default:
            return state;
     }
}

here i am doing the count of added items if that product is already exist in cart then increase quantity of that product. But i am getting type error because of null reference.

TypeError: Unable to get property 'id' of undefined or null reference ->(const pid = productToAdd.id)

Here is my productcomponent page :

    import React, { Component } from 'react';
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
import {addToCart} from '../../action/cartAction';
import {Button} from 'react-bootstrap';

class ProductComponent extends Component{
    constructor(props){
        super(props);
        this.state ={
            radioSearch : '',
            filteredData: this.props.products
        }
    }
    handleClick = (id)=>{
        this.props.addToCart(id); 
    }
    /** some other handler **/
    render(){
        let itemList = this.state.filteredData.map(item=>{
            return(
                <div className="card" key={item.id}>
                        <div className="card-image">
                            <img src={item.img} alt={item.title}/>
                            <span className="card-title">{item.title}</span>
                        </div>

                        <div className="card-content">
                            <p><b>Discount: {item.discount}%</b></p>
                            <p><b>Price: {item.price}$</b></p> <Button variant="dark" onClick={()=>{this.handleClick(item.id)}}>ADD TO CART</Button>
                        </div>
                 </div>

            )
        })

        return(
            <div className="container">
                /** some other code **/
                <div className="box">
                    {itemList}
                </div>
            </div>
        )
    }
}
const mapStateToProps = (state)=>{
    return {
        products: state.productReducer.products
    }
  }
function mapDispatchToProps(dispatch) {
return bindActionCreators({
    addToCart
}, dispatch);

export default connect(mapStateToProps,mapDispatchToProps)(ProductComponent)

here is my cartcomponent

import React, { Component } from 'react';
import { connect } from 'react-redux'
import { bindActionCreators } from 'redux'
import {removeFromCart} from '../../action/cartAction';

class cartComponent extends Component {
    handleRemove(id){
        this.props.removeFromCart(id);
    }
    render() {
        console.log(this.props.cartItems.length);
        let cartProducts = this.props.cartItems.length ?
        (
            this.props.cart.map(item=>{
                return(
                       
                    <li className="collection-item avatar" key={item.id}>
                                <div className="item-img"> 
                                    <img src={item.img} alt={item.img} className=""/>
                                </div>
                            
                                <div className="item-desc">
                                    <span className="title">{item.title}</span>
                                    <p>{item.desc}</p>
                                    <p><b>Price: {item.price}$</b></p> 
                                    <p>
                                        <b>Quantity: {item.quantity}</b> 
                                    </p>
                                    <button className="waves-effect waves-light btn pink remove" onClick={()=>{this.handleRemove(item.id)}}>Remove</button>
                                </div>
                                
                            </li>
                     
                )
            })
        ):
        (
            <p>Your cart is empty</p>
        )
        return(
            <div className="container">
                <div className="cart">
                <h5>You have ordered:</h5>
                    <ul className="collection">
                        {cartProducts}
                    </ul>
                </div>
            </div>
        )
    }
}

function mapStateToProps(state) {
    return {
        cartItems : state.productReducer.cartItems
    }
}

function mapActionsToProps(dispatch) {
    return bindActionCreators({
        removeFromCart
    }, dispatch);
}


export default connect(mapStateToProps,mapActionsToProps)(cartComponent);

i have tried many things but it is not adding product to cart. what are the changes needed to make it work?

Here is my source code : source code

Upvotes: 0

Views: 1156

Answers (2)

Rigers Leka
Rigers Leka

Reputation: 483

In productReducer file you should push the item into state.cartItems

if (!productToAdd) {
        productToAdd = products.find(obj => obj.id === action.id);
        count = 1;
     ADD row-> state.cartItems.push(productToAdd);
}

In this approach, if you don't enter a specified quantity of the product, it will be automatically placed to the cart as one item.

Upvotes: 0

Brian Thompson
Brian Thompson

Reputation: 14385

It looks like the way you map the action to props does not match the actual usage of the function.

You map it like this:

addToCart: (id)=>{dispatch(addToCart(id))}

The action just passes its parameter as payload meaning payload is equal to id:

export const addToCart= payload =>({
  type: ADD_TO_CART,
  payload
});

But you expect the payload to be an object like this:

const { id } = action.payload;

You need to make them match. Either pass the action an object:

addToCart: (id)=>{dispatch(addToCart({id}))}

Or use the payload as the id:

const id = action.payload;

The result of the code as is, is that id is undefined, meaning no productToAdd.

Upvotes: 1

Related Questions