在应用程序和私有库中同时包含 React 的正确方法是什么?(来自重复反应的无效钩子调用警告)



我有一个"monorepo",一个由几个使用 React 的小项目组成的大项目。

我试图将它们分解为三个独立的存储库,让我们称它们为CoreApplication1Application2

Core是两个应用程序的依赖关系,Core依赖于 React,因为它定义了一些 React 组件类。 这两个应用程序也都使用 React。

当我尝试一起构建这一切(使用 Parcel bundler(时,我得到了一个最终的捆绑包,它在运行时在一个(但不是两个(应用程序中发出无效钩子调用警告。

在该页面上(或在错误消息中(,它说错误可能是由以下一个引起的:

  1. 你可能有不匹配的 React 和 React DOM 版本。
  2. 你可能违反了钩子规则。
  3. 你可能在同一个应用程序中有多个 React 副本。

我已经检查了 #1 不是真的,我什至没有以我知道的任何方式使用钩子,所以问题似乎是 React 的多个版本。

我从阅读中了解到,我的Core库将 React 声明为依赖项是错误的,它应该在peerDependencies中声明它。 这使得应用程序停止给出错误,但它也使我的核心库开始出现一堆打字稿错误,并且无法运行单元测试(依赖于 React,使用 Jest/Enzyme 来渲染和验证 DOM(。

由于在peerDependencies中指定 React 导致它没有安装在Corenode_modules中,我决定我可能应该在CorepeerDependenciesdevDependencies中包含 React。 这会再次修复核心库,但会破坏应用程序。

我不太确定以下内容:

  • 为什么我的一个应用程序由于重复的 React 副本而另一个应用程序失败,因为它们看起来彼此非常对称。
  • 为什么,即使我只在peerDependencies中指定 React,在Core中指定devDepenencies,我仍然会在依赖应用程序中获得 React 的副本
  • 用于将Core引入应用程序的方法是否与此有关。 (我正在尝试的一种方法是 package.json,我将核心指定为"文件:../"样式的网址。 另一种选择是使用"yarn link",或者可能同时执行这两项操作,我不确定这是否会对应用程序文件夹下方node_modules中的最终内容或捆绑的内容有任何影响(

在应用程序和库中同时包含 React 的正确方法是什么,这样这两个项目都有可用的 React,但最终应用程序中没有重复导致此钩子错误(或者,只是占用额外的空间(。

回答我自己的问题。

我发现以下问题很有帮助:https://github.com/facebook/react/issues/14257

在关于解决此问题的方法的注释中提出了各种不同的建议,要么npm link,要么yarn linkreact 库从库到应用程序,反之亦然。 这些看起来都很有希望,因为这个想法是确保所有对 React 的不同引用实际上都指向同一个地方。 不幸的是,这些都不适合我。(例如杰里格林和卡斯在该期中的回答(

另一个用户dcecile建议使用webpack的alias功能,但我没有使用webpack。

resolve: {
alias: { react: require.resolve("react") }
},

Parcel 具有类似的alias功能,但不能以完全相同的方式使用,因为它在 package.json 文件中使用,因此不能像 webpack 的 js 配置文件中那样调用require.resolve之类的东西。

我最终找到了一种方法来使用 Parcel 的alias功能来做我想做的事情,基于用户 jaredpalmer https://github.com/jaredpalmer/tsdx/issues/64 的另一个示例。 在我的情况下,我将其添加到应用程序的 package.json 中,它似乎摆脱了重复问题和"无效钩子调用"错误:

"alias": {
"react": "../my-core-library/node_modules/react",
},

相关内容

最新更新