【发布时间】:2021-08-09 09:31:24
【问题描述】:
我一直在用 React 编写一个应用程序(电子商务,作为一个项目,遵循一个教程)。引用购物车对象时,我收到“TypeError:无法读取未定义的属性“长度””的错误。这是一些背景背景。我正在使用 App.js 组件顶部附近的 useState 挂钩生成购物车对象:
const [cart, setCart] = useState({});
在 App.js 再往下一点,console.log 语句执行时没有错误提示购物车对象存在:
console.log(cart);
但是,当我尝试将购物车对象传递给 App.js 渲染部分中的购物车组件时,会生成上述错误(例如“TypeError: Cannot read property 'length' of undefined”)。为什么会发生这种情况,我该如何解决?
这里是 App.js 的代码
import React, { useState, useEffect } from 'react'
import { commerce } from './lib/commerce';
import { Products, Navbar, Cart } from './components';
const App = () => {
const [products, setProducts] = useState([]);
const [cart, setCart] = useState({});
const fetchProducts = async () => {
const { data } = await commerce.products.list();
setProducts(data);
}
const fetchCart = async () => {
setCart(await commerce.cart.retrieve());
}
const handleAddToCart = async (productID, quantity) => {
const item = await commerce.cart.add(productID, quantity);
setCart(item.cart);
}
useEffect(() => {
fetchProducts();
fetchCart();
}, []);
console.log(cart);
return (
<div>
<Navbar totalItems={cart.total_items} />
{/* <Products products={products} onAddToCart={handleAddToCart} /> */}
<Cart cart={cart} />
</div>
)
}
export default App
这是我将购物车对象传递到的组件(购物车)的代码:
import React from 'react'
import { Container, Typography, Button, Grid } from "@material-ui/core";
import useStyles from './styles';
const Cart = ({ cart }) => {
const isEmpty = !cart.line_items.length;
const classes = useStyles();
const EmptyCart = () => {
<Typography variant="subtitle1">
You have no items your shopping cart..
</Typography>
}
const FilledCart = () => {
<>
<Grid container spacing={3}>
{
cart.line_items.map((item) => (
<Grid item xs={12} sm={4} key={item.id}>
<div>{item.name}</div>
</Grid>
))
}
</Grid>
<div className={classes.cardDetails}>
<Typography variant="h4">
Subtotal: { cart.subtotal.formatted_with_symbol }
</Typography>
<div>
<Button className={classes.emptyButton} size="large" variant="contained" type="button" color="secondary">Empty Cart</Button>
<Button className={classes.checkoutButton} size="large" variant="contained" type="button" color="primary">Checkout</Button>
</div>
</div>
</>
}
return (
<Container>
<div className={classes.toolbar} />
<Typography className={classes.title} variant="h3">Your shopping cart</Typography>
{
isEmpty ? <EmptyCart /> : <FilledCart />
}
</Container>
)
}
export default Cart
【问题讨论】:
-
嗯
cart最初只是一个空对象。这意味着cart.line_items将在初始渲染中未定义。因此,您会收到该错误。在 API 调用完成之前,您不应渲染购物车,跟踪请求的状态并在等待获取购物车内容时显示一些加载 UI -
@Jayce444 如果是这样,我就不会打印出信息。这意味着,这不是实际问题。 fetchCart 函数实际上是在获取信息,这就是被打印出来的内容。
-
能否分享一下购物车对象中的数据。
-
您获取购物车数据的代码是异步的,正如@Jayce444 所建议的那样,它最初会使您的组件崩溃,因为
const isEmpty = !cart.line_items.length;将失败,因为它是一个空对象。你可以这样做const isEmpty = !cart.line_items || !cart.line_items.length;来防止这种情况发生吗? -
@saksh73 这是正在打印的日志:!Valid XHTML
标签: javascript reactjs