2

I'm trying to share a React component I've created through a local hosted npm repo.

To do that I created the React component with typescript, transpiled it to js and published the resulting code to the repo. But when I install this package in an existing project (a basic create-react-app project with typescript) and try to use that component - My app tried to compile it for a few minutes and I fail to load that component. Sometimes if I wait a few minutes I see this error - although the component was tested and works:

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:

  1. You might have mismatching versions of React and the renderer (such as React DOM)
  2. You might be breaking the Rules of Hooks
  3. 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.'

I've copied the same component to be embedded in the app and not installed by npm - it worked. I tried to strip the component to the bare minimum - it still takes a long time.

The steps to reproduce are easy:

I've shared the component in github:

https://github.com/ymoran00/example-stackoverflow-react

To build it you need to run npm install and then npm run build. the result will be generated in the lib folder. You can then go into the lib folder and run:

npm link

Then create a new typescript create-react-app project:

npx create-react-app my-app --template typescript

Go inside it and run:

npm link login-component

This will install the linked package.

Now go to App.tsx and import the package:

import LoginContainer from 'login-component/LoginContainer';

And use it in the App:

<LoginContainer onLogin={()=> {alert('success')}}/>

Run the app with npm start.

The App will open the browser - but nothing will load. It's kind of stuck on build or whatever - I don't know what happens there. If you'll take a look at the component you'll see it's quite a basic one with Material-UI.

Yoav Moran
  • 107
  • 9

2 Answers2

1

The first place that I looked was your package.json file because it most likely that you are dealing with reason #1:

You might have mismatching versions of React and the renderer (such as React DOM)

I see that you are including react and react-dom as dependencies for your component. You should move these from dependencies to peerDepenedencies. You likely want to move @material-ui/core and @material-ui/icons to peerDependencies as well. Right now React is being bundled with your component and your component uses its own React version rather than the one in your app. You want to make it so that projects that use your component are expected to include React on their own.

For more information about why you should use peerDependencies, see this question:

Linda Paiste
  • 38,446
  • 6
  • 64
  • 102
  • You're right - that's my mistake in the github project I created for stackoverflow, not in the issue I had. I've updated the project in github. Sorry for the mistake. – Yoav Moran Apr 11 '21 at 06:46
1

It seems that the main problem I had in the process is using npm link. It causes problems when combined with hooks - that's why I get this hooks error. See also in this thread:

https://github.com/facebook/react/issues/13991

So instead of using npm link I've started using npm-sync and it seems to solve the problem.

Yoav Moran
  • 107
  • 9