question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Potential performance issues with using forwardRef

See original GitHub issue

Do you want to request a feature or report a bug?

Bug (assuming that a potential drop in perf counts as a “bug”)

What is the current behavior?

I’ve been setting up a rudimentary perf benchmark harness for React-Redux over in https://github.com/reduxjs/react-redux/issues/983 , so that we can compare performance between builds of React-Redux as we work on version 6. The harness runs one or more benchmark apps in headless Puppeteer, running them once to capture FPS values and a second time to capture Chrome trace reports automatically.

Currently, there’s only one benchmark app: a “stock ticker”-type stress test that measures FPS by using the fps-emitter package (which relies on requestAnimationFrame). It’s rough, but it does show meaningful differences in FPS values as we swap between different React-Redux builds and change the number of connected components in the benchmark.

We have two WIP candidate PRs for React-Redux v6: https://github.com/reduxjs/react-redux/pull/995 and https://github.com/reduxjs/react-redux/pull/1000 . Initial testing showed that PR 995 was almost as fast as our existing 5.0.7 version, while PR 995 was slower in some runs. However, my initial push of the 995 branch did not include use of React.forwardRef, while the 1000 branch already had that added.

I spent Saturday adding forwardRef and a couple other pieces of functionality to the 995 branch, then re-ran the benchmarks. Per ourcomments in the 983 issue, we saw that the 995 branch had suddenly gotten slower, and that removing forwardRef from the 1000 branch sped things up by a few FPS.

This is admittedly a very artificial stress test scenario, but it’s also likely that React-Redux apps can have hundreds or thousands of connected components at once, so the potential slowdown seems concerning.

If the current behavior is a bug, please provide the steps to reproduce and if possible a minimal demo of the problem. Your bug will get fixed much faster if we can run your code and it doesn’t have dependencies other than React. Paste the link to your JSFiddle (https://jsfiddle.net/Luktwrdm/) or CodeSandbox (https://codesandbox.io/s/new) example below:

The current perf benchmark repo is at https://github.com/markerikson/benchmark-react-redux-perf . It uses UMD builds of React-Redux so that it can easily switch which build is being used. Several UMD builds are already committed there in the root of the repo. 6.0-mark is the 995 branch, and 6.0-greg is the 1000 branch. They can be reproduced by building their respective branches from the PRs. I’ve been hand-copying the UMD build artifact from my React-Redux clone over to this benchmark folder and renaming it to whatever seems appropriate.

Clone the repo, yarn to install, yarn perf to build and run the benchmark. Number of connected components can be modified in src/constants.js (requires rebuilding). The harness determines which UMD build versions to run based on an array in perfBenchmark.js, around line 11 (const VERSIONS = ["5.0.7", "6.0-mark"]).

What is the expected behavior?

That there would be minimal to no impact in perf when forwardRef is used to wrap a component such as a HOC, and that HOC is used widely in an application.

Which versions of React, and which browser / OS are affected by this issue? Did this work in previous versions of React?

I’ve been testing this with Puppeteer 1.6.2, on Windows 10. It looks like the locally installed version of Chromium is 69.0.3494.0 .

Current version of React is 16.4.2, UMD build (as React-Redux UMD expects that both React and Redux are also global variables). I have not tested against a prior version of React, as we are specifically targeting 16.4+ with this next version of React-Redux.

Issue Analytics

  • State:closed
  • Created 5 years ago
  • Reactions:2
  • Comments:32 (11 by maintainers)

github_iconTop GitHub Comments

6reactions
cellogcommented, Aug 26, 2018

Ok 😃 probably best to pretend it doesn’t exist until then unless you are allowed to give a hint how we can prepare the code to be ready for it. All very mysterious and exciting, are you all releasing a new iPhone?

4reactions
natewcommented, May 3, 2019

I’m mostly curious at to why the difference seems so large between development and production. I have a virtual table that renders a decent amount of items, even in a small window. In production, it’s basically fine for me. In development, I see this:

image

And so on for ~50 items. As you can see forwardRef is most of the work here, which seems odd.

Read more comments on GitHub >

github_iconTop Results From Across the Web

What are the benefits of using forwardRef instead of passing ...
One assumption that comes to a mind is that with forwardRef React won't try to serialize the passed element, but I'm pretty sure...
Read more >
Using forwardRef in React to clean up the DOM
In this tutorial, we'll review the concept of forwarding refs in React and how it helps us manage interactions with the DOM.
Read more >
If having hundreds of components impacts performance, that's ...
Some things like React.forwardRef and React.memo should be considered when doing that, but that approach will become more and more popular (and ...
Read more >
Why custom react hooks could destroy your app performance
Exploring performance implications of custom React hooks and how not to shoot yourself in the foot when writing or using them.
Read more >
forwardRef - Angular
Descriptionlink. For instance, forwardRef is used when the token which we need to refer to for the purposes of DI is declared, but...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found