尝试创建可共享的 React 组件 - 但无法导入它
Trying to create a shareable React component - but failing to import it
我正在尝试分享我通过本地托管的 npm 存储库创建的 React 组件。
为此,我使用打字稿创建了 React 组件,将其转换为 js 并将生成的代码发布到 repo。但是当我在现有项目(一个带有 typescript 的基本 create-react-app 项目)中安装这个包并尝试使用该组件时 - 我的应用程序试图编译它几分钟但我未能加载该组件。有时,如果我等待几分钟,我会看到此错误 - 虽然该组件已经过测试并且可以正常工作:
Error: Invalid hook call. Hooks can only be called inside of the body
of a function component. This could happen for one of the following
reasons:
- You might have mismatching versions of React and the renderer (such as React DOM)
- You might be breaking the Rules of Hooks
- You might have more than one copy of React in the same app See https://reactjs.org/link/invalid-hook-call for tips about how to debug
and fix this problem.'
我复制了相同的组件以嵌入到应用程序中,而不是通过 npm 安装 - 它有效。我试图将组件剥离到最低限度 - 它仍然需要很长时间。
重现步骤很简单:
我在 github 中分享了组件:
https://github.com/ymoran00/example-Whosebug-react
要构建它,您需要 运行 npm install 然后 npm 运行 build。
结果将在 lib 文件夹中生成。
然后你可以进入 lib 文件夹和 运行:
npm link
然后新建一个 typescript create-react-app 项目:
npx create-react-app my-app --template typescript
进去然后运行:
npm link login-component
这将安装链接包。
现在转到 App.tsx 并导入包:
import LoginContainer from 'login-component/LoginContainer';
并在应用程序中使用它:
<LoginContainer onLogin={()=> {alert('success')}}/>
运行 带有 npm start 的应用程序。
应用程序将打开浏览器 - 但不会加载任何内容。它有点卡在构建或其他什么东西上——我不知道那里发生了什么。如果您查看该组件,您会发现它是一个非常基本的组件 Material-UI.
我首先查看的是您的 package.json
文件,因为您很可能正在处理原因 #1:
You might have mismatching versions of React and the renderer (such as React DOM)
我看到您将 react
和 react-dom
作为组件的依赖项。您应该将它们从 dependencies
移至 peerDepenedencies
。您可能还想将 @material-ui/core
和 @material-ui/icons
移动到 peerDependencies
。现在 React 与你的组件捆绑在一起,你的组件使用它自己的 React 版本,而不是你应用程序中的版本。您希望使用您的组件的项目能够独立包含 React。
有关为什么要使用 peerDependencies
的更多信息,请参阅此问题:
- What's the difference between dependencies, devDependencies and peerDependencies in npm package.json file?
我在这个过程中遇到的主要问题似乎是使用npm link
。
与钩子结合使用时会导致问题 - 这就是我收到此钩子错误的原因。
另请参阅此线程:
https://github.com/facebook/react/issues/13991
所以我没有使用 npm link,而是开始使用 npm-sync,它似乎解决了问题。
我正在尝试分享我通过本地托管的 npm 存储库创建的 React 组件。
为此,我使用打字稿创建了 React 组件,将其转换为 js 并将生成的代码发布到 repo。但是当我在现有项目(一个带有 typescript 的基本 create-react-app 项目)中安装这个包并尝试使用该组件时 - 我的应用程序试图编译它几分钟但我未能加载该组件。有时,如果我等待几分钟,我会看到此错误 - 虽然该组件已经过测试并且可以正常工作:
Error: Invalid hook call. Hooks can only be called inside of the body of a function component. This could happen for one of the following reasons:
- You might have mismatching versions of React and the renderer (such as React DOM)
- You might be breaking the Rules of Hooks
- You might have more than one copy of React in the same app See https://reactjs.org/link/invalid-hook-call for tips about how to debug and fix this problem.'
我复制了相同的组件以嵌入到应用程序中,而不是通过 npm 安装 - 它有效。我试图将组件剥离到最低限度 - 它仍然需要很长时间。
重现步骤很简单:
我在 github 中分享了组件:
https://github.com/ymoran00/example-Whosebug-react
要构建它,您需要 运行 npm install 然后 npm 运行 build。 结果将在 lib 文件夹中生成。 然后你可以进入 lib 文件夹和 运行:
npm link
然后新建一个 typescript create-react-app 项目:
npx create-react-app my-app --template typescript
进去然后运行:
npm link login-component
这将安装链接包。
现在转到 App.tsx 并导入包:
import LoginContainer from 'login-component/LoginContainer';
并在应用程序中使用它:
<LoginContainer onLogin={()=> {alert('success')}}/>
运行 带有 npm start 的应用程序。
应用程序将打开浏览器 - 但不会加载任何内容。它有点卡在构建或其他什么东西上——我不知道那里发生了什么。如果您查看该组件,您会发现它是一个非常基本的组件 Material-UI.
我首先查看的是您的 package.json
文件,因为您很可能正在处理原因 #1:
You might have mismatching versions of React and the renderer (such as React DOM)
我看到您将 react
和 react-dom
作为组件的依赖项。您应该将它们从 dependencies
移至 peerDepenedencies
。您可能还想将 @material-ui/core
和 @material-ui/icons
移动到 peerDependencies
。现在 React 与你的组件捆绑在一起,你的组件使用它自己的 React 版本,而不是你应用程序中的版本。您希望使用您的组件的项目能够独立包含 React。
有关为什么要使用 peerDependencies
的更多信息,请参阅此问题:
- What's the difference between dependencies, devDependencies and peerDependencies in npm package.json file?
我在这个过程中遇到的主要问题似乎是使用npm link
。
与钩子结合使用时会导致问题 - 这就是我收到此钩子错误的原因。
另请参阅此线程:
https://github.com/facebook/react/issues/13991
所以我没有使用 npm link,而是开始使用 npm-sync,它似乎解决了问题。