为什么无限滚动响应不会看到函数map()中的数据?

问题描述 投票:1回答:4

我有这个代码的问题:

<InfiniteScroll
  dataLength={beers.length}
  next={fetchMoreBeers}
  hasMore={true}
  loader={<p>Loading ...</p>}
  endMessage={<p id="beers-end">No more beers :(</p>}
>
  {beers.map((beer, index) => (
    <div key={index}>
      <Link
        to={{
          pathname: `/beer/${beer.id}`,
          state: { beer: beer.id },
        }}
      >
        <div className="beer-wrapper">
          <div className="beer">
            <img
              className="beer-img"
              src={beer.image_url}
              alt={beer.name}
            />
            <p className="beer-name">
              {beer.name.length < 15
                ? `${beer.name}`
                : `${beer.name.substring(0, 20)}...`}
            </p>
            <p className="beer-tagline">
              {beer.tagline.length < 20
                ? `${beer.tagline}`
                : `${beer.tagline.substring(0, 25)}...`}
            </p>
          </div>
        </div>
      </Link>
      <Route path="/beer/:id" component={Beer} />
    </div>
  ))}
</InfiniteScroll>;

当页面滚动时,会发生错误:

“TypeError:无法读取未定义的属性'id'”

对于这一行:

pathname: `/beer/${beer.id}`,

这看起来像InfiniteScroll没有看到map()函数中的数据....

也许你们有些人知道如何解决这个问题?

谢谢你的任何提示!

javascript reactjs typeerror infinite-scroll
4个回答
0
投票

也许问题在于模板文字。当我们直接添加模板文字时,它会抛出这样的问题。我的项目经历过同样的经历。

也许你可以尝试以下方式

render(){
  const { beers } = this.props;
  const beerItems = beers.map((beer, index) => {
      let pathName = `/beer/${beer.id}`;
              return (
                <div key={index}>
                    <Link to={{ 
                        pathname: {pathName},
                        state: {"beer": beer.id}
                    }} >
                        <div className="beer-wrapper">       
                            <div className="beer">
                                <img className="beer-img" src={beer.image_url} alt={beer.name} />
                                <p className="beer-name">
                                    {beer.name.length < 15 ? beer.name : beer.name.substring(0, 20) }
                                </p>
                                <p className="beer-tagline">
                                    {beer.tagline.length < 20 ? beer.tagline : beer.tagline.substring(0, 25) }
                                </p>
                            </div>
                        </div>
                    </Link>
                    <Route path="/beer/:id" component={Beer} />
                </div>    
            )
            }

  return(
    <InfiniteScroll
            dataLength={beers.length}
            next={fetchMoreBeers}
            hasMore={true}
            loader={<p>Loading ...</p>}
            endMessage={<p id="beers-end">No more beers :(</p>}
        >    
            {beerItems}
        </InfiniteScroll>
  )
}

0
投票

也许在undefined数组中存储了beers值。尝试过滤掉它们,如下所示:

beers.filter(Boolean).map((beer, index) => ( 
  // ... 
)

另外,我注意到hasMore道具总是设置为true。要查看它是否有帮助,请尝试以下方法:

<InfiniteScroll
  dataLength={beers.length}
  next={fetchMoreBeers}
  hasMore={beers.length < 25} // or hasMore={this.state.hasMore}
  loader={<p>Loading ...</p>}
  endMessage={<p id="beers-end">No more beers :(</p>}
> ...

编辑:

您正在使用Array.from({ length: 20 }))。输出数组将包含20个undefined值。这就是为什么你应该考虑beers.filter(Boolean)

我想这就是你的真实含义:

this.setState({ 
  items: this.state.beers.concat(Array.from(this.state.beers))
})

要么:

this.setState({ 
  items: [...this.state.beers, ...this.state.beers]
})

0
投票

您应该在获取啤酒时检查状态代码。即使请求失败,fetch仍会让你做你的事情。如果超出端点数据限制,您将把这些数据添加到啤酒阵列:

{
  "statusCode": 400,
  "error": "Bad Request",
  "message": "Invalid query params",
  "data": [{
    "param": "per_page",
    "msg": "Must be a number greater than 0 and less than 80",
    "value": "100"
  }]
}

正如你所看到的,那里没有id param会让这个奇怪的错误出现。

包括一个json模式验证器(如https://ajv.js.org/)以确保数据是预期的格式将是一个完美的选择。


0
投票

我认为这个问题是因为这个Api中的数据记录限制。

© www.soinside.com 2019 - 2024. All rights reserved.