Javascript 获取失败会导致无限组件生命周期循环

Javascript 获取失败会导致无限组件生命周期循环,javascript,reactjs,redux,rxjs,redux-observable,Javascript,Reactjs,Redux,Rxjs,Redux Observable,对于连接的容器,我有一个由高阶减速机(如下所示)包装的减速机来捕获和处理错误。在componentDidMount期间调用提取请求失败时,连接的容器将卸载自身componentWillUnmount。这将导致容器中出现无限循环,因为它将再次装载,获取将失败,并且容器将卸载自身 你知道为什么在连接组件中使用高阶减速器会导致这种情况吗 处理高阶减速机时出错: export const errorHandler = (reducer: (state: any, action: { type: stri

对于连接的容器,我有一个由高阶减速机(如下所示)包装的减速机来捕获和处理错误。在
componentDidMount
期间调用提取请求失败时,连接的容器将卸载自身
componentWillUnmount
。这将导致容器中出现无限循环,因为它将再次装载,获取将失败,并且容器将卸载自身

你知道为什么在连接组件中使用高阶减速器会导致这种情况吗

处理高阶减速机时出错:

export const errorHandler = (reducer: (state: any, action: { type: string }, initialState: any) => {}) => {
    const errorState = fromJS({
        error: {
            hasError: false,
            message: "",
        },
    });

    const initialState = errorState.merge(reducer(undefined, { type: undefined }, undefined));

    return (state = initialState, action) => {
        switch (action.type) {
            case ACTIONS.SET_ERROR:
                return state.setIn(["error", "hasError"], true)
                    .setIn(["error", "message"], action.message);

            case ACTIONS.CLEAR_ERROR:
                return state.set("error", errorState.get("error"));

            default:
                return reducer(state, action, initialState);
        }
    };
};
示例容器:

class Page extends Component {
    componentDidMount() {
        this.props.fetch(....);
    }
    componentWillUnmount() {
        this.props.clearData();
        this.props.cancelRequests();
    }
}

export default connect(
    (state) => ({
        error: state.data.get("error", ""),
    }),
    {
        clearError,
        clearData,
        cancelRequests,
    },
)(Page);
减速器示例:

export fetch = () => ({
   type: ACTIONS.FETCH
});

export default errorHandler((state, action) => {
   switch(action.type) {
     default:
        return state;
   }
}));
史诗:


我认为您只需要捕获错误,而不是让代码捕获异常

try {
   this.props.fetch(....);
}
catch (e) {
   //Do whatever is appropriate to handle the fetch failure. Maybe you want...
   this.setState({ error: {hasError: true, message: '' + e});
}

我认为上面的setState()调用不适合您预期的reducer实现,但这是一个单独的问题,您可以解决(或询问更多问题)。问题的主要部分似乎是停止卸载/重新装载行为。

根据我们在评论中的对话:


通常,组件会卸载,因为它们的父级不再呈现它们。孩子的父母长什么样?您可能会在这里查找组件卸载的原因


我不知道有哪种情况下组件可以自行卸载(无需黑客)

谢谢您的帮助!我忘了提到我使用的是Redux Observable,所以在本例中,
this.props.fetch()
只是分派一个操作,而不是执行请求。不幸的是,用try/catch包装它是行不通的。原始帖子中的示例已更新。通常,组件会卸载,因为它们的父级不再呈现它们。孩子的父母长什么样?(我实际上不知道有什么情况下组件可以自行卸载,但可能是这样)这正是问题所在。在进一步研究这个问题之后,我发现一个父组件使用了相同的errorHandler()高阶减速机。每当触发setError()时,父级将捕获事件,并重新引发其子级(包括此处的Page)。不再使用全局setError()操作完全解决了这个问题。
try {
   this.props.fetch(....);
}
catch (e) {
   //Do whatever is appropriate to handle the fetch failure. Maybe you want...
   this.setState({ error: {hasError: true, message: '' + e});
}