0

我有:

onKeyPress(id, e) {
        if(e.key == 'Enter') {
            this.saveField(id, e.target.value);
        }
    }

    onBlur(id, e) {
        this.saveField(id, e.target.value);
    }

    saveField(id, date) {
        this.setState({
            updatingField: true
        })
        this.context.executeAction(SetJobChaserDate, {date: date, id: id});
        this.setState({
            editingChaser: false,
            editingTrackingSent: false,
            updatingField: false
        })
    }

问题是,在动作触发后似乎 setState 立即触发,因此没有给我另一个组件的效果。

如何仅在操作完成后设置状态(无论成功或失败)?


这是我的行动:

import qwest from 'qwest';

export default function SetJobChaserDate(actionContext, payload) {
    return qwest.post('jobs/set/chaser-date', {id: payload.id, date: payload.date}, {responseType: 'json'})
        .then(function (response) {

            actionContext.dispatch('RECEIVED_JOBS_DATA', {data: response.response, clear: false})

        })
}

import { EventEmitter } from 'events';

class JobStore extends EventEmitter {

    constructor() {
        super();
        this.jobs = new Map();
        this.counts = {};
        this.loading = false;
    }

    handleJobsData(payload) {
        if (payload.clear === true) {
            this.jobs = new Map();
        }
        payload.data.jobs.forEach((job) => {
            this.jobs.set(job.id, job);
        });
        if(payload.data.counts) {
            this.counts = payload.data.counts;
        }
        this.loading = false;
        this.emit('change');

    }

    handleReceiving() {
        this.loading = true;
        this.emit('loading');
    }

    handleCounts(payload) {
        console.log(payload)
    }

    getCounts() {
        return this.counts;
    }

    getJobs() {
        return this.jobs;
    }

    dehydrate () {
        return this.jobs;
    }

    rehydrate (state) {

    }

}

JobStore.dispatchToken = null;

JobStore.handlers = {
    'RECEIVED_JOBS_DATA': 'handleJobsData',
    'RECEIVED_COUNTS'   : 'handleCounts',
    'RECEIVING_JOB_DATA': 'handleReceiving'
};

JobStore.storeName = 'JobStore';

export default JobStore;

更新:

componentWillReceiveProps() {
        this.context.getStore(JobStore).on('change', () => {
            this.setState({
                updatingField: false
            });
        });
    }

    onKeyPress(id, e) {
        if (e.key == 'Enter') {
            this.saveField(id, e.target.value);
        }
    }

    onBlur(id, e) {
        this.saveField(id, e.target);
    }

    saveField(id, target) {
        console.log(target)
        this.setState({
            updatingField: true
        })
        this.context.executeAction(SetJobChaserDate, {date: target.value, id: id});
        this.setState({
            editingChaser: false,
            editingTrackingSent: false
        })
    }
4

1 回答 1

0

您正在使用一种updating状态,表明您的流程是异步的。您正在调度的代码确实是一个承诺,并在流程完成时调度一个动作:'RECEIVED_JOBS_DATA'

因此,您应该将 移动为updatingField来自商店的组件道具,并在动作开始和结束时在您的减速器中更改。

这样,您可以只this.props.updatingField在您的组件中使用,该值将来自商店并取决于您的外部请求的当前状态。

这样,您将遵循一种 React/Flux 最佳实践,即首选全局状态而不是本地状态。

于 2016-05-11T12:34:36.837 回答