Explore React Compiler and Integrate with examples #909
Explore React Compiler and Integrate with examples #909Muhammad-Bin-Ali wants to merge 11 commits intomainfrom
Conversation
|
commit: |
deathbyknowledge
left a comment
There was a problem hiding this comment.
Looks good, just one small change
|
@Muhammad-Bin-Ali what did you learn from doing this? I see you've changed the configs, but could we simplify any react code? What are the goals/benefits of adding the compiler? |
From what I gathered, the React Compiler primarily focuses on adding memoization where needed. In our examples, there's not many, if any, places to simplify code because we don't use I still think we could benefit to adding it to our |
|
I would love to see an experiment where we take an example with useMemo, run it without the compiler, then run it with, and see what's different. why are we using useMemo in those places? |
Hmmm good point. Let me see what I can set up. Also, there are places in our examples where we can simplify the code a little. React compiler also removes the need for adding |
|
I added a demo to this branch. It also outputs the JSX intermediate representation. After running it with and without compiler, there should be two files, one with compiled output and one uncompiled. TLDR of differences;The compiler adds a per-component cache array that is checked before values/functions/elements are accessed. Future implications:Based on some online research, people's mileage with integrating React compiler will vary. For example, there's a Tanstack Tables library that React Compiler breaks, but can easily be fixed by adding // BEFORE: works everywhere, with or without the compiler
const refreshPermissions = useCallback(async () => {
const result = await agent.call("getPermissions");
setIsReadonly(!result.canEdit);
}, [agent, connected]);
useEffect(() => {
refreshPermissions();
}, [refreshPermissions]);
//=====================================================
// AFTER: someone removes useCallback in a cleanup PR
// "the compiler handles memoization now"
const refreshPermissions = async () => {
const result = await agent.call("getPermissions");
setIsReadonly(!result.canEdit);
};
useEffect(() => {
refreshPermissions();
}, [refreshPermissions]);
// ❌ Without the compiler: new function ref every render
// → effect re-fires → calls getPermissions → setState
// → re-render → new ref → effect re-fires → infinite loopIf we choose to remove the Lastly, I'd be very hesitant to make any changes to the existing code I amend my previous claim of it being a good addition to the codebase. It's hard to say if it's worth the problems that it could lead to in the future. It could be a good addition if we had browser-based behaviour testing, but even then, experientially, not all UI behaviour can be tested programatically. |
threepointone
left a comment
There was a problem hiding this comment.
Yeah I was concerned this would be the outcome. React folks trying. to be a bit too clever here. I'm going to block this from landing while we figure it out. Thanks so much for diving into this @Muhammad-Bin-Ali, it was worth it.
Integrate React Compiler across all examples
Summary
babel-plugin-react-compilerto all 9 React examples via the@vitejs/plugin-reactBabel configenable_ctx_exportscompatibility flag from the codemode example'swrangler.jsoncChanges
codemodevite.config.tsplaygroundvite.config.tsmcpvite.config.tsmcp-clientvite.config.tstictactoevite.config.tsworkflowsvite.config.tsresumable-stream-chatvite.config.tsa2avite.config.tscross-domainvite.config.tsHow to integrate React Compiler
package.json):react()plugin's Babel config invite.config.ts:For full details, see the official introduction: https://react.dev/learn/react-compiler/introduction
Linting (optional)
An ESLint plugin is available to identify components the compiler cannot optimize:
When the ESLint rule reports an error, it means the compiler will skip optimizing that specific component or hook. This is safe — the compiler continues optimizing everything else. You don't need to fix all violations immediately; address them at your own pace to gradually increase the number of optimized components.
Note: This repo uses Oxlint, not ESLint, so this plugin is not currently wired up. It can be run alongside Oxlint if full Rules-of-React validation is desired.
Verifying the compiler is working
Components optimized by React Compiler will show a "Memo ✨" badge in React DevTools:
npm run start)If the compiler is working:
useMemois requiredGenerated by OpenCode