首页 > 解决方案 > 如何在 React 中过滤来自 API 和 setState 的 JSON 数据

问题描述

单击过滤器按钮后,第一个过滤器会返回正确的数据,但是当调用第二个过滤器方法时,状态中的数组会发生突变(或销毁?)。我对每个函数都使用了 setState 并且无法弄清楚为什么没有恢复数组的初始状态。

当我导入 JSON 数据的本地副本时,此应用程序正在运行。注释代码块确实表明过滤器函数适用于本地数据,但不适用于我的服务器的 fetch 方法返回的相同 JSON 数据。

import React from "react";
import { Button, Row, Col } from "react-bootstrap";
import AutoList from './AutoList';
// import autoData from '../autoData.json';

const API = "https://MY_SERVER/autoData.json";

class GetAutos extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      autos: [],
    };
  }

  fetchAutoData() {
      fetch(API)
        .then(autoData => autoData.json())
        .then(autoData =>
            this.setState({
                autos: autoData, 
                isLoading: false,
            })
        )
        .catch(error => this.setState({ error, isLoading: false }));

  }

  componentDidMount() {
      this.fetchAutoData();
      // this.setState(() => ({ autos: autoData }));
  }


  render() {

    const { autos } = this.state;

    let onResetArray = () => {
        this.setState({ autoData: this.state.autos })
        //console.log(autos)
      }

    let filterFord = () => {
        const fordAutos = autos.filter( (auto) => auto.title.includes("Ford"));
        // const fordAutos = autoData.filter( (auto) => auto.title.includes("Ford"));

        this.setState({ autos: fordAutos });
    }


    let filterChevy = () => {
        const chevyAutos = autos.filter( (auto) => auto.title.includes("Chevrolet"));
        // const chevyAutos = autoData.filter( (auto) => auto.title.includes("Chevrolet"));

        this.setState({ autos: chevyAutos });
    }

    let filterJeep = () => {
        const jeepAutos = autos.filter( (auto) => auto.title.includes("Jeep"));
        // const jeepAutos = autoData.filter( (auto) => auto.title.includes("Jeep"));

        this.setState({ autos: jeepAutos });
    }
    return (
        <div className="container">
            <Row className="mb-4">
                <Col>
                    <Button event-key="reset-autos" onClick={onResetArray}>All Cars</Button>
                </Col>
                <Col>
                    <Button event-key="ford-autos" onClick={filterFord}>Filter Ford</Button>
                </Col>
                <Col>
                    <Button event-key="chevy-autos" onClick={filterChevy}>Filter Chevy</Button>
                </Col>
                <Col>
                    <Button event-key="jeep-autos" onClick={filterJeep}>Filter Jeep</Button>
                </Col>
            </Row>


        <AutoList autos={ this.state.autos } />
        </div>

    );
  }
}
export default GetAutos;

我希望随后单击按钮以过滤状态中的数据集。相反,单击过滤由 .filter() 方法创建的数组。我的代码适用于我的 JSON 数据的本地导入,但不适用于获取的 JSON。

标签: javascriptreactjs

解决方案


当您使用过滤结果设置状态时,您正在从源中删除条目。相反,您应该将过滤后的结果存储在不同的键中。

例如像这样的东西。

const jeepAutos = autos.filter( (auto) => auto.title.includes("Jeep"))
this.setState({
  filteredAutos: jeepAutos
})

然后在渲染时你会像这样使用它

<AutoList autos={ this.state.filteredAutos } />

请记住,最初filteredAutos 将是空的,因此要查看所有您需要在通过之前检查过滤的项目

<AutoList autos={ filteredAutos.length > 0 ? filteredAutos : autos } />

简单的例子


推荐阅读