react hooks源代码总体运行初解(一)

作者:知鸟 聂凡坤

这篇文章是从源代码的角度剖析react hooks,在开始之前,对于react hooks的重要性以及为什么需要用函数组件可以阅读:

一、阅读源码的误区

首先我们需要找到源代码,不少萌新小伙伴可能会从node_modules中的react模块包中去找hooks的源代码,如下图

你所看到的只有这些hooks的定义,而其值的实现方式都是以var dispatcher = resolveDispatcher();再由这个dispatcher去调用对应的不同的事件,对于resolveDispatcher()方法的实现也会看得一头雾水,ReactCurrentDispatcher在这个源代码中啥都没有。所以从node_modules中react模块包解读hooks是行不通的。

二、从哪里开始阅读源码

正确的方式是从github react 的仓库下载源代码仓库能进行解读。下载好了之后我们可以看到packages有32个模块包,接下来的讲解都在packages路径下,跟hooks强相关的reactreact-reconciler两个模块包。

上面的图可以看到这是真正意义上的专门的定义react hooks的本源,再继续寻找ReactCurrentDispatcher我们可以看到是引入了一个类型Dispatcher(派发者),派发者类型定义如图:

如上文件只暴露出的type Dispatcher里只提供了常用的如useStateuseEffect等方法的类型定义,怎样才能发现更多有用的信息呢?

三、如何快速定位方法的源码实现

源代码研究不下去的时候应该换个角度,既然是只是定义类型,那一定有其他地方也会调用该类型从而获取hooks的更深层的实现。所以这里用了一个取巧的方式:在react-reconciler中搜索Dispatcher

可以看到两个文件引用了ReactInternalTypes中定义的Dispatcher打开ReactFiberHooks.old.js之后就可以发现新大陆。

这里可以看到引入类Dispatcher的实现有三个对象HooksDispatcherOnMount(hooks派发在组件加载时),HooksDispatcherOnUpdate(hooks派发在组件更新时),HooksDispatcherOnRerender(hooks派发在组件渲染。这三个对象都是集中在renderWithHooks的函数之中(图不贴,请读者自行寻找)。

本着追本溯源的方式我们找寻renderWithHooks的引用文件。在ReactFiberBeginWork.old.js中都使用在了updateFunctionComponent函数中,而这个函数是调用在了case FunctionComponent中,而代码下方的case ClassComponent所调用的方法的的updateClassComponent,所以,如下

由于找到代码是采用的取巧的方式,再回过头总结下hooks的实现为一个词--分片任务调度。对于分片这个词感到陌生的小伙伴可以拜读下这篇文章

这篇文章中有提到两个阶段,Reconcile阶段和Commit阶段从这两个阶段分别对应ReactFiberBeginWork.old.jsReactFiberCommitWork.old.js(现在文件中oldnew代码都一样,可能facebook官方要做优化重构所以复制一份出来用old,new作为区分)。

四、在reconcile阶段调用核心方法renderWithHooks

reconcile阶段当解析到为函数组件时会调用核心方法renderWithHooks

此方法会根据当前的分片任务中的current属性是否有任务去判断执行HooksDispatcherOnMount还是HooksDispatcherOnUpdate,在渲染阶段react调度器会适时得执行HooksDispatcherOnRerender

五、在commit阶段对hook执行队列解除

commit阶段当解析到为函数组件时会对hook执行队列解除:

对于commitHookEffectListUnmount字面意思为解除提交过的hooks执行队列,将当前的一个个执行的hooksEffect置空或者销毁。

文章篇幅有限,蜻蜓点水,只对hooks怎么通过react的调度机制运行以及如何找寻hooks的源码进行解读,整体运行的机制还需要各位看官自行再看源代码解读。

下一个篇幅将介绍hooks的那些方法源码的实现。

原文链接:juejin.im

上一篇:最简单的map,filter,forEach,every,some的使用教学
下一篇:1024 奇妙冒险全结局 + jsliang 自定义算法题目

相关推荐

  • 高效阅读Github源代码

    三种办法。如果你主要看前端项目的代码,直接看第三种。 1,用Chrome插件Octotree,左侧会出现树形结构,方便你浏览源代码。 地址: https://chrome.google.com/we...

    3 年前
  • 面试题:Hooks 与 React 生命周期的关系

    React 生命周期很多人都了解,但通常我们所了解的都是 单个组件 的生命周期,但针对 Hooks 组件、多个关联组件(父子组件和兄弟组件) 的生命周期又是怎么样的喃?你有思考和了解过吗,接下来我们将...

    1 年前
  • 面试官: 聊一聊 HOC、Render props、Hooks

    在以前我们可能会看到很多文章在分析 HOC 和 render props, 但是在 2020 年 ,我们有了新欢 “hook” . 本篇文章会分析 hook , render props 和 HOC ...

    8 个月前
  • 重学Hooks——useEffect

    useEffect Dan在Overreacted上发表的文章深入浅出,本文只针对个人之前不理解的点进行思考,采用了他的案例,参考了他的文章——useEffect的完整指南. 在我看来,Effec...

    4 个月前
  • 访问控制允许在请求的资源上存在起始头。因此,不允许访问源代码。

    访问控制允许在请求的资源上存在起始头。因此,不允许访问源代码。 ...

    3 年前
  • 终于搞懂 React Hooks了!!!!!

    学习总结! 从三个纬度学习记录: 为什么🤔️ 怎么用🔨 知识点⛽️ useState 为什么要使用useState? useState 的出现是 : 在函数组件里面使用 class的s...

    9 个月前
  • 精读《怎么用 React Hooks 造轮子》

    1 引言 上周的 精读《React Hooks》 已经实现了对 React Hooks 的基本认知,也许你也看了 React Hooks 基本实现剖析(就是数组),但理解实现原理就可以用好了吗?学的是...

    2 年前
  • 精读《React Hooks》

    1 引言 React Hooks 是 React 16.7.0-alpha 版本推出的新特性,想尝试的同学安装此版本即可。 React Hooks 要解决的问题是状态共享,是继 render-prop...

    2 年前
  • 精读《React Hooks 最佳实践》

    简介 React 16.8 于 2019.2 正式发布,这是一个能提升代码质量和开发效率的特性,笔者就抛砖引玉先列出一些实践点,希望得到大家进一步讨论。 然而需要理解的是,没有一个完美的最佳实践规范,...

    1 年前
  • 精读《React Hooks 数据流》

    文章地址...

    8 个月前

官方社区

扫码加入 JavaScript 社区