繁体   English   中英

React 在线商店 - createContext 不会在页面重新加载时保留数据

[英]React Online Store - createContext doesn't keep data on page reload

在学习 React 的过程中,我决定尝试创建自己的在线商店。 在学习和实施 createContext 功能和处理之后,我遇到了它不在页面刷新/重新加载上保留数据的问题。

最简单的解决方案可能是将数据存储到 localStorage 中,但我不知道如何将 localStorage 项作为整个 createContext (contextValue) 数组来实现和处理,并在每个上下文的 function 更改时保持更新。

在 React 中有什么简单的解决方案吗? 或者在整体上处理这种上下文的最佳 JS 解决方案是什么?

import { createContext, useState } from "react";
import { productsArray, getProductData } from "./productsConfig";

export const CartContext = createContext({
    items: [],
    getProductQuantity: () => {},
    addOneToCart:       () => {},
    removeOneFromCart:  () => {},
    deleteFromCart:     () => {},
    getTotalCost:       () => {}
});

export function CartProvider({children}) {
    const [cartProducts, setCartProducts] = useState([]);

    function getProductQuantity(id) {
        const quantity = cartProducts.find(product => product.id === id)?.quantity;
        
        if (quantity === undefined) {
            return 0;
        }

        return quantity;
    }

    function addOneToCart(id) {
        const quantity = getProductQuantity(id);

        if (quantity === 0) {
            setCartProducts(
                [
                    ...cartProducts,
                    {
                        id: id,
                        quantity: 1
                    }
                ]
            )
        } else { // is in cart
            setCartProducts(
                cartProducts.map(
                    product =>
                    product.id === id                               
                    ? { ...product, quantity: product.quantity + 1 }
                    : product                                       
                )
            )
        }
    }
    
    function removeOneFromCart(id) {
        const quantity = getProductQuantity(id);

        if (quantity === 1) {
            deleteFromCart(id);
        } else {
            setCartProducts(
                cartProducts.map(
                    product =>
                    product.id === id                               
                    ? { ...product, quantity: product.quantity - 1 }
                    : product                                       
                )
            )
        }
    }

    function deleteFromCart(id) {
        setCartProducts(
            cartProducts =>
            cartProducts.filter(currentProduct => {
                return currentProduct.id !== id;
            })
        )
    }

    function getTotalCost() {
        let totalCost = 0;
        cartProducts.map((cartItem) => {
            const productData = getProductData(cartItem.id);
            totalCost += (productData.price * cartItem.quantity);
        });
        return totalCost;
    }

    const contextValue = {
        items: cartProducts,
        getProductQuantity,
        addOneToCart,
        removeOneFromCart,
        deleteFromCart,
        getTotalCost
    }

    return (
        <CartContext.Provider value={contextValue}>
            {children}
        </CartContext.Provider>
    )
}

export default CartProvider;

您应该使用上下文来管理购物车内部 state 并使用本地存储来保持您的购物车 state 持久(或者您可以使用 session 存储方法)。 因此,使用本地存储将您的 cartProducts 数组保存为 object

localStorage.setItem('cart', JSON.stringify(newCartProductsArray))

并在添加/删除功能上更新它,更新 function 应该覆盖相同的键值。

要在刷新后恢复您的 state,请使用 CartProvider 中的 useEffect 挂钩。

useEffect(() => {
  const savedCartState = JSON.parse(localStorage.getItem('cart'));
  setCartProducts(savedCartState);
}, []);

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM