React(16.4.1)setState()使用react-select组件在当前onChange事件之后更新状态一onChange事件

时间:2018-10-12 20:46:02

标签: javascript reactjs setstate

我有2个反应选择组件,我希望设置的行为是,当用户从两个选择组件中进行选择时(顺序无关紧要),那么将触发ajax从服务器中提取数据。必须完全从这两个组件中进行选择,才能完全填充ajax调用的GET参数。

我对react-select元素上的onChange事件有以下两个处理程序:

filterSiteSelect(selection) {
    const siteId = selection.id;
    const siteName = selection.name;

    this.setState({
        siteId, siteName
    }, this.getTableData());
}

filterLineTypeSelect(selection) {
    const lineTypeId = selection.id;
    const lineTypeName = selection.name;

    this.setState({
        lineTypeId, lineTypeName
    }, this.getTableData());
}

我的getTableData()方法如下:

getTableData() {
    const {
        productId, siteId, lineTypeId, stages, tableUrl
    } = this.state;

// tableUrl = `p=field&t=view&gapi=1&product_id=${productId}&site_id=${siteId}&line_type_id=${lineTypeId}&stage_ids=${stages}`

    if (productId && siteId && lineTypeId && !_.isEmpty(stages)) {
        Axios.get(tableUrl)
            .then((result) => {
                this.setState({
                    rawData: { ...result.data.data }
                });
            });
    }
}

我遇到的行为是,当用户从第二个选择框中选择一个选项时,ajax调用不会触发。用户需要返回并选择其他内容来触发ajax调用,然后使用他们选择的第一个选择。

我还尝试通过此代码对ajax调用使用ComponentDidUpdate()(当我更改为getTable()后,我从每个setState()调用中删除了componentDidUpdate(prevState)数据) :

componentDidUpdate(prevState) {
    const {
        siteId, lineTypeId, stages
    } = this.state;

    if (lineTypeId !== prevState.lineTypeId && siteId !== prevState.siteId && !_.isEqual(stages, prevState.stages)) {
        this.getTableData();
    }
}

但是,当使用componentDidUpdate()生命周期方法时,它将反复反复地触发ajax,而不会停止,我相信这是因为setState()从未更新用户交互的最后一个选择组件的状态

所以我认为我在使用/理解setState()方法时做错了(或者问题出在react-select组件中……)。

任何对我要完成的事情的见解,帮助或讨论将不胜感激!

2 个答案:

答案 0 :(得分:1)

当您将第二个参数传递给setState()时,例如setState({foo: bar}, <something>)<something>应该是一个回调函数,它在setState()完成更新后会被调用。在您的代码中,没有传递函数this.getTableData作为参数,而是传递了从调用返回的表达式 this.getTableData(),在这种情况下为undefined

在您的代码中:

filterSiteSelect(selection) {
    const siteId = selection.id;
    const siteName = selection.name;

    this.setState({
        siteId, siteName
    }, this.getTableData());
}

filterLineTypeSelect(selection) {
    const lineTypeId = selection.id;
    const lineTypeName = selection.name;

    this.setState({
        lineTypeId, lineTypeName
    }, this.getTableData());
}

当您同步调用setState()并向队列添加状态更新时,您还同步调用this.getTableData(),它立即运行,检查状态变量中的一些布尔值,也许尝试执行ajax调用等

尝试简单地删除(),以便将函数作为参数直接传递到setState中,而不是意外地调用函数。 :)

filterSiteSelect(selection) {
    const siteId = selection.id;
    const siteName = selection.name;

    this.setState({
        siteId, siteName
    }, this.getTableData);
}

filterLineTypeSelect(selection) {
    const lineTypeId = selection.id;
    const lineTypeName = selection.name;

    this.setState({
        lineTypeId, lineTypeName
    }, this.getTableData);
}

答案 1 :(得分:0)

setState的第二个参数是回调。这意味着您应该传递对要调用的函数的引用,而不是调用函数本身。

this.setState({
    siteId, siteName
}, this.getTableData());

应该是

this.setState({
    siteId, siteName
}, this.getTableData);