【问题标题】:How to share hooks between React components with composition如何通过组合在 React 组件之间共享钩子
【发布时间】:2020-10-04 09:19:38
【问题描述】:

我有一个高阶组件,它为一组相似的组件添加了通用功能。出于讨论的目的,我将调用 HOC Wrapper 和孩子 CompACompB 等。

Wrapper 是 connected,它处理与 Redux 存储的交互以及 API 交互。它发送的数据归被包装的孩子所有,所以我通过道具将 API/调度函数从 Wrapper 传递给孩子。现在 CompA、CompB 等都有一个 props.doStuff 函数,该函数在 Wrapper 中定义了一次。

这没关系,但是决定何时调用doStuff 函数的事件是 CompA、CompB 等中本地状态的变化。所以我在孩子之间复制/粘贴相同的 useEffects。 ..

function CompA(props) {
  const [data, setData] = useState({});
  useEffect( () => {
    if (props.doStuffNow === true) {
      props.doStuff(data);
    }
  }, [props.something]);
  return <div>CompA</div>
}

function CompB(props) {
  const [differentData, setDifferentData] = useState({});
  useEffect( () => {
    if (props.doStuffNow === true) {
      props.doStuff(differentData);
    }
  }, [props.something]);
  return <div>CompB</div>
}

这不是 D.R.Y。我真的很想将useEffect 等移动到 Wrapper 类中,并允许 CompA 和 CompB 到 extend 该类。

然而,React documentation strongly recommends composition over inheritance 使用更高阶的组件。链接的文章甚至说他们从未遇到过继承优于组合的情况。

那么我错过了什么?有没有办法让我使用 HOC 使这段代码干燥?我可以通过道具以某种方式传递useEffects 吗?如果我只是跟随我的直觉,天会不会塌下来:class CompA extends Wrapper... ??

【问题讨论】:

    标签: javascript reactjs inheritance composition


    【解决方案1】:

    创建一个名为 useDoStuff 的新钩子,它执行 useEffect 钩子,然后在任何需要的地方创建 useDoStuff(props)

    function useDoStuff(props) {
      const [data, setData] = useState({}):
      useEffect(...)
    }
    
    function CompA (props) {
      useDoStuff(props);
      ...
    }
    
    function CompB (props) {
      useDoStuff(props);
      ...
    }
    
    

    【讨论】:

    • 我不确定我是否完全理解您的代码。 useDoStuff 是否在 Wrapper 类的范围内定义?如果是这样,它不需要作为道具传递吗?我也不清楚useState 将如何在 CompA/B 的范围内可用...datasetData 不会包含在函数的本地范围内,因此在 CompA/ 中不可用乙?
    • 您实际上经常从您的useDoStuff 挂钩返回您感兴趣的变量。毕竟你的逻辑你做return [data, setData]或者如果你更喜欢return { data, setData }
    • 还有另一个问题:钩子中的共享功能涉及调度(Redux)动作。如果自定义钩子超出了connected Wrapper 的范围,我们如何使它们在自定义钩子中可用?
    • 我知道我们可以将动作创建者作为道具传递,但这不是开始创建我们试图避免的相同的下降链吗?
    • 如果适合您的需要,您可以将状态移出钩子并进入本地组件,并将附加参数传递给钩子(钩子需要做的任何信息)。这个想法只是将共享功能封装在一个地方,并在需要的地方重用它。
    猜你喜欢
    • 1970-01-01
    • 2015-08-25
    • 1970-01-01
    • 1970-01-01
    • 2020-08-07
    • 1970-01-01
    • 2020-11-08
    • 2019-01-31
    • 1970-01-01
    相关资源
    最近更新 更多