Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[material-ui] Lazy-loaded Collapse with unmountOnExit causes infinite loop #42457

Closed
tajbowness opened this issue May 30, 2024 · 8 comments
Closed
Assignees
Labels
component: Collapse The React component package: material-ui Specific to @mui/material

Comments

@tajbowness
Copy link

tajbowness commented May 30, 2024

Steps to reproduce

Link to live example: (required)

https://stackblitz.com/edit/react-cfhjx1?file=Demo.js

Steps:

  1. Press dropdown

Current behavior

Using unmountOnExit on collapse causes infinite loop.

Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops.

Removing unmountOnExit prop from collapse fixes issue. I'd like to use unmountonExit though so I hope to find a solution.

Lazy loading is also likely another reason why this issue is occuring. But for my project it's necessary otherwise, I'd get these prompts

Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: object

Code is from MUI Docs only changed the imports as that is how my project is.

React / Remix / Vite

Expected behavior

Dropdown :)

Context

Dropdown :)

Your environment

https://stackblitz.com/edit/react-cfhjx1?file=Demo.js

Search keywords: Collapse Infinite unmountOnExit

@tajbowness tajbowness added the status: waiting for maintainer These issues haven't been looked at yet by a maintainer label May 30, 2024
@tajbowness
Copy link
Author

Wrapping the code inside of collapse with Suspense also fixes the issue (lazy, i guess). But you don't get the very first transition, instead its pop ups. The issue seems to be caused by lazy.

@aarongarciah aarongarciah changed the title Collapse with unmountonExit causes infinite loop. [material-ui] Collapse with unmountonExit causes infinite loop. May 31, 2024
@aarongarciah aarongarciah added package: material-ui Specific to @mui/material component: Collapse The React component labels May 31, 2024
@aarongarciah aarongarciah self-assigned this May 31, 2024
@aarongarciah aarongarciah changed the title [material-ui] Collapse with unmountonExit causes infinite loop. [material-ui] Collapse with unmountOnExit causes infinite loop May 31, 2024
@aarongarciah aarongarciah changed the title [material-ui] Collapse with unmountOnExit causes infinite loop [material-ui] Lazy loaded Collapse with unmountOnExit causes infinite loop May 31, 2024
@aarongarciah aarongarciah changed the title [material-ui] Lazy loaded Collapse with unmountOnExit causes infinite loop [material-ui] Lazy-loaded Collapse with unmountOnExit causes infinite loop May 31, 2024
@aarongarciah
Copy link
Member

Lazy loading is also likely another reason why this issue is occuring. But for my project it's necessary otherwise, I'd get these prompts

@tajbowness are you receiving these errors for all components or only those coming from @mui/material? I'd recommend looking for the root cause.

I've been testing a bit and this is the summary is:

  • The issue happens with the combination of lazy (without Suspense) + unmounOnExit.
  • Wrapping lazy-loaded components with Suspense makes the issue disappear but the initial transition is lost.
  • unmountOnExit with regularly loaded components works fine.
  • The error is thrown in the Transition component from the react-transition-group, which Collapse uses under the hood. Unclear what causes it.

I'd always recommend wrapping lazy-loaded components in Suspense, especially the ones displayed after user interaction. See this example adapted from the React docs.

I think we should focus on a more realistic scenario like this one I adapted from your demo: playground. Collapse wraps a lazy-loaded component wrapped in Suspense. The problem in this case is that the transition doesn't work when the component is lazy-loaded for the first time.

@siriwatknp @DiegoAndai do you remember similar issues with Material UI transition components?

@zannager zannager removed the status: waiting for maintainer These issues haven't been looked at yet by a maintainer label May 31, 2024
@tajbowness
Copy link
Author

Hey @aarongarciah, thanks for the reply!

This error that I mentioned earlier,
Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: object

Has only been occurring with @mui/material. These are my projects packages

Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops.

This has been the first time I've encountered this error. Having no initial transition isn't much of a concern. But I'm wondering now how to solve the other error (expected a string (for built-in components)) as it floods my server log and inspect console. Do you have any insight on this?

@aarongarciah
Copy link
Member

@tajbowness can you provide a playground or repo where we can reproduce the Element type is invalid issue? I wonder if this could be a CJS/ESM issue.

@aarongarciah aarongarciah added the status: waiting for author Issue with insufficient information label Jun 4, 2024
@aarongarciah
Copy link
Member

@tajbowness this could be helpful/related #41960 (comment)

@tajbowness
Copy link
Author

tajbowness commented Jun 4, 2024

@aarongarciah I've tried that, unfortunately, it still persists.

I've made some changes and swapped from using lazy to import Tooltip from '@mui/material/Tooltip'; this has solved a couple of issues within my project, which is great, but Element type is invalid still logs, doesn't impact anything, just only floods the server.

I think you may be right with that it may be a CJS/ESM issue (My project is ESM). I am using Vite, which I believe it doesn't fully support CJS, but I've tried vite-plugin-commonjs to make them compatible, but it didn't help.

So I'm currently importing like this import Tooltip from '@mui/material/Tooltip';

Doing this, import {Tooltip} from '@mui/material/Tooltip';, prompts this vite error:

[vite] Named export 'Tooltip' not found. The requested module '@mui/material/Tooltip' is a CommonJS module, which may not support all module.exports as named exports.
CommonJS modules can always be imported via the default export, for example using:

import pkg from '@mui/material/Tooltip';
const {Tooltip} = pkg;

I'm unable to create a repo that reproduces the error, I know that's not very helpful, but it seems the issue is with Vite anyways. What do you think? I think this can be closed.

@github-actions github-actions bot added status: waiting for maintainer These issues haven't been looked at yet by a maintainer and removed status: waiting for author Issue with insufficient information labels Jun 4, 2024
@aarongarciah
Copy link
Member

I expect issues with Vite + CJS to go away once #30671 is completed cc @DiegoAndai.

I'll rename this issue so we can track the problem with the initial animation when a component is lazy-loaded.

@aarongarciah aarongarciah removed the status: waiting for maintainer These issues haven't been looked at yet by a maintainer label Jun 5, 2024
@aarongarciah
Copy link
Member

Thinking about it a bit more, it makes sense the initial animation doesn't work because there is no content within Collapse when its children are lazy-loaded. I'm closing it because the original issue with the infinite loop it's "resolved".

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
component: Collapse The React component package: material-ui Specific to @mui/material
Projects
None yet
Development

No branches or pull requests

3 participants