首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >高阶组件被多次调用

高阶组件被多次调用
EN

Stack Overflow用户
提问于 2017-07-10 17:13:06
回答 1查看 796关注 0票数 2

我已经创建了以下高阶组件:

代码语言:javascript
复制
const baseComponent = (WrappedComponent: React.ComponentClass<any>) => (props: IKeyValue) => {
  if (props.isLoading) {
    return (
      <LoadingSpinnerComponent shown={true} />
    );
  }

  return (
    <WrappedComponent {...props} />
  );
};

这会导致此组件被无限期地调用。( myComponent中的componentDidMount意味着这个组件正在被重新创建)。

我以以下方式使用它:

代码语言:javascript
复制
export default connect(
  mapStateToProps,
  dispatchToProps,
)(baseComponent(myComponent)) as React.ComponentClass<any>;

卸下if部件时:

代码语言:javascript
复制
  if (props.isLoading) {
    return (
      <LoadingSpinnerComponent shown={true} />
    );
  }

该组件将只被调用一次。我试着在react库代码内部进行调试,但神奇的是它对我来说是个奇迹。有什么想法吗?

提前感谢!

编辑:

完整代码:myComponent

代码语言:javascript
复制
class MiniCatalogContainer extends React.PureComponent<IProps, void> {
  public componentDidMount() {
    const { fetchCatalog} = this.props;
    fetchCatalog({path});
  }

  public render() {
    ...
  }
}

export default connect(
  mapStateToProps,
  dispatchToProps,
)(baseComponent(MyComponent)) as React.ComponentClass<any>;

promise-middleware

代码语言:javascript
复制
import { Dispatch } from 'react-portal/src/interfaces';
import isPromise from 'react-portal/src/utils/is-promise';

interface IOptions {
  dispatch: Dispatch;
}

export default function promiseMiddleware({ dispatch }: IOptions) {
  return (next: Dispatch) => (action: any) => {
    if (!isPromise(action.payload)) {
      return next(action);
    }

    const { types, payload, meta } = action;
    const { promise, data } = payload;
    const [ PENDING, FULFILLED, REJECTED ] = types;

   /**
    * Dispatch the pending action
    */
    dispatch( { type: PENDING,
                ...(data ? { payload: data } : {}),
                ...(meta ? { meta } : {}),
    });

    /**
     * If successful, dispatch the fulfilled action, otherwise dispatch
     * rejected action.
     */
    return promise.then(
      (result: any) => {
        dispatch({
          meta,
          payload: result,
          type: FULFILLED,
        });
      },
      (error: any) => {
        dispatch({
          meta,
          payload: error,
          type: REJECTED,
        });
      },
    );
  };
}

解决方案:

正如@Shleng注意到的,这个循环是因为我在组件内部调用了fetch。我最终得到了一个简单的解决方案:

代码语言:javascript
复制
const baseComponent = (WrappedComponent: React.ComponentClass<any>) => (props: IKeyValue) => {
      if (props.isLoading) {
        return (
          <LoadingSpinnerComponent shown={true} />
          <WrappedComponent {...props} />
        );
      }

      return (
        <WrappedComponent {...props} />
      );
    };
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2017-07-10 21:45:02

因为您在包装组件的componentDidMount中调用fetchCatalog,所以工作流会导致如下所示的循环:

代码语言:javascript
复制
mount WrappedComponent -> fetch -> mount Spinner -> loaded -> mount WrappedComponent -> fetch (loop!)

isLoading: false       -> true                   -> false                            -> true
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/45008060

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档