Everyone's Talking About This React Exploit
By Josh tried coding
Summary
## Key takeaways - **Critical RCE in React Server Components**: There is an unauthenticated remote code execution vulnerability in React server components, allowing anyone to execute code inside your server components. It was reported on November 29th by Lachland Davidson exploiting a flaw in how React decodes payloads. [00:34], [01:03] - **CVSS 10.0 Perfect Score**: This vulnerability is disclosed as CVE-2025-55182 and rated a CVSS of 10.0, the most severe score on the 0-10 scale. Even default Next.js apps from create-next-app in versions 15 and 16 are vulnerable with no code changes. [01:43], [02:24] - **Affects Next.js App Router**: Not only React but Next.js is affected since it builds on these features, especially the app router allowing untrusted inputs to influence server-side execution. Every Next.js 15 and 16 version is vulnerable. [02:07], [04:51] - **Minor Patches Auto-Update**: React and Next.js released minor patch versions like 19.2.1 for every vulnerable release, so running npm update or bun upgrade automatically puts you on a safe version without other changes. [03:30], [05:22] - **Fix Uses hasOwnProperty Check**: The patch adds a hasOwnProperty check before accessing module.exports[metadataName] to prevent prototype pollution via the inheritance chain, ensuring only actual object properties are accessed. [11:10], [11:42] - **Pure Client Apps Safe**: Apps not using a server or frameworks supporting React Server Components like pure SPAs are not affected, but modern server-based React with Next.js or React Router needs upgrading. [05:40], [06:05]
Topics Covered
- React Server Components Enable RCE
- Default Next.js Apps Vulnerable
- Minor Patches Auto-Update
- Prototype Pollution Enables Exploit
Full Transcript
Not going to lie, man. It's not looking too hot for the JavaScript ecosystem at the moment. First npm gets hacked. And
the moment. First npm gets hacked. And
now, just a week later, the biggest React exploit in probably the entire year. In this video, I want to find out
year. In this video, I want to find out together with you what might have been the problem, how the React team fixed it within hours, and what the problem was in the first place. So, there's a
critical security vulnerability in React server components published on December 3rd by the React team. So let's get into this and see what was the problem and how did they fix it. So there is an
unauthenticated remote code execution vulnerability in React server components. That sounds really scary
components. That sounds really scary man. Basically anyone can execute code
man. Basically anyone can execute code that they want inside of your server components. That's scary and they
components. That's scary and they recommend upgrading immediately. On
November 29th, Lachland Davidson reported a security vulnerability in React that allows unauthenticated remote code execution by exploiting a flaw in
how React decodes payloads sent to the React server function endpoints. And now
we're going to take a look at the commit that fixes this here in a bit. I already
opened this up. But before we do that, let's understand really what the problem is. Even if your app does not implement
is. Even if your app does not implement any React server function endpoints, it may still be vulnerable if your app supports React server components. So
even if you don't use React server functions, which I personally don't, I think there are nicer ways to fetch data with React Query, for example, and a
type safe RPC endpoint, well, you're still vulnerable to this exploit. So
this is scary, man. This vulnerability
was disclosed as CVE 202555182 and is rated a CVSs of 10.0. CVSS is a way to score vulnerabilities on a scale
of 0 to 10. 10 being the most severe and this is a straight 10 out of 10. So this
is really really bad because as I found in this article critical vulnerabilities in React and NexJS everything you need to know. Yes, not only React is
to know. Yes, not only React is affected. Of course, Nex.js builds on
affected. Of course, Nex.js builds on these features. So, NexJS is also
these features. So, NexJS is also affected. The interesting thing here,
affected. The interesting thing here, basically, this is an exploit in the React server components flight protocol.
Even the default configurations are vulnerable. Like, if you just create a
vulnerable. Like, if you just create a standard NexJS app with create next app and don't change anything about it, you are vulnerable in some versions like
every 15 and every 16 version. So all of the newer ones, they can be exploited with no code changes by the developer.
So that's that's kind of nutty, man.
Even if you don't change anything, you're still vulnerable. And the
exploitation requires only a crafted HTTP request and has shown near 100% reliability in testing. The flaw stems from insecure des serialization in the
RC payload handling logic allowing attacker control data to influence serverside execution.
So pretty much the only way around this is to patch your version. So what React and NexJS both did is first off firewall patches on the Verscell side. For
example, if you happen to deploy on Versell, well, the firewall is kind of a hot fix without upgrading the package, but you should still probably upgrade the package as soon as possible. So,
what the teams did is release new versions for basically every vulnerable version before that, right? So, 19.2 was affected. Well, they published 19.2.1, a
affected. Well, they published 19.2.1, a minor patch. So even if you just say bun
minor patch. So even if you just say bun upgrade or npm update, whatever package manager you use, you're automatically going to be put on a safe version even
without any other changes. That's a good way to go about it. We can see that quite a few people already downloaded these patches. Like 19.2.1 about 3,000
these patches. Like 19.2.1 about 3,000 people here. For 19.0, it's 7,000
people here. For 19.0, it's 7,000 people. This is probably nowhere close
people. This is probably nowhere close to the amount of people that installed the vulnerable version, 19.0.0. zero.
Which is why I want to be really careful when we get to the technical part because still a lot a lot of people are vulnerable to this and probably
especially vibe coded apps man do you really think vibe coders people who just prompt cursor will really care about this I don't know man I hope so but still so many people are vulnerable to
this let's take a look at how this looks on nextj site because obviously react is affected in nextjs it's pretty much the same thing. This vulnerability
same thing. This vulnerability originates in the upstream React implementation that Nex.js, especially the server components built on top of this advisory tracks the downstream
impact on NexJS applications using the app router. It allows untrusted inputs
app router. It allows untrusted inputs to influence serverside execution behavior under specific conditions in attacker could craft requests that trigger unintended server execution
paths. This can result in remote code
paths. This can result in remote code execution in unpatched environments and basically every NexJS5 every NexJS 16 version is affected. Again here they
published minor patches. So as soon as you upgrade your dependencies you are good and you're on a patch version. So
all you need to do is say like npm update and that should fix it with these minor patches. You can see 15 has
minor patches. You can see 15 has patches and 16 as well just in you know semantic versioning. these very tiny
semantic versioning. these very tiny ones that npm knows to automatically update. Now, there are certain
update. Now, there are certain conditions though when you're not affected. If your app react code does
affected. If your app react code does not use a server whatsoever, you're good. Your app is not affected by this
good. Your app is not affected by this vulnerability. If your app does not use
vulnerability. If your app does not use a framework bundler or bundler plug-in that supports React server components, your app is not affected by this vulnerability. So if you just use React
vulnerability. So if you just use React as a spa, as a single page application purely on the client, you are fine. But
if you're using Next, React Router, Wahoo, basically any other way to interact with the more modern server-based React, well, just upgrade
your packages, man. So how did this how did this work? Vulnerability overview.
React server functions allow a client to call a function on a server. That's the
idea, right? It's pipes safe. It's very
convenient. It's honestly a really good way to execute code on the server, but it's also the problem here. React
provides integration points and tools that frameworks and bunders use to help React code run on both the client and the server. React translates requests on
the server. React translates requests on the client into HTTP requests, which are forwarded to a server. So, it looks like you're calling a function on the client,
but really crosses the network boundary.
React turns this function call into an HTTP request and it's sent to the server. On the server, React translates
server. On the server, React translates the HTTP request into a function call and returns the needed data to the client. So, a classic RPC pattern. An
client. So, a classic RPC pattern. An
unauthenticated attacker could craft a malicious HTTP request to any server function endpoint that when deserialized by React achieves remote code execution
on the server. The attacker can run code in your environment in your server.
Further details of the vulnerability will be provided after the rollout of the fix is complete which makes a lot of sense because so many people are still vulnerable to this right so I want to be
very careful with the technical part because so many people still haven't updated but I also want to provide a basic overview kind of how this
vulnerability might have worked.
[Music] Now let's take a look at a P here
published on GitHub. But this P is very very likely not the actual issue, right?
This is probably not it. This is
artificially more dangerous than it needs to be. So take this vulnerability PLC with a very very big grain of salt, but it does help us kind of understand
how this vulnerability might have worked. So let's take a look at this
worked. So let's take a look at this with a very big grain of salt. Basically
we have a require module function in this example which might or might not exist in the actual react. But the
vulnerable part is right here at the very end when we are parsing a module right here. This statement is
right here. This statement is problematic because we are accessing an object in this case module exports at
the index of a user controlled input but we're not checking if whatever is metadata 2 or what that evaluates to is
a property of the object which is problematic. So the issue in this case
problematic. So the issue in this case would be that the module exports at the index of metadata 2 checks along the prototype chain the entire inheritance
chain of the object and not just its own properties. If we have an object let's
properties. If we have an object let's call it like in this example module exports cons module exports and let's just define it as an empty object. This
metadata 2 property we are accessing on the object module exports can be influenced by the user. So this could evaluate for example to module exports
dot constructor right or I guess in a different notation like here we could access the module exports at the property of constructor for example or
any other property that exists well probably not emojis any other property that exists along the inheritance chain right for example constructor so this
actually evaluates to a function and like this the user could get access to code they are not supposed to get access to. Right? The problem here is the
to. Right? The problem here is the constructor is not a property of the actual object. It's along the
actual object. It's along the inheritance chain. So the better way to
inheritance chain. So the better way to do it would be to check if the module exports has own property and we can check for constructor and this check
module exports.ropy
module exports.ropy constructor evaluates to false because it's not an actual property of the object. It's a property of the object
object. It's a property of the object instantiation above the module exports.
And this here is the patch that fixed the problem. The patch flight reply
the problem. The patch flight reply server with fixes from ReactFlight client. So we already know this was a
client. So we already know this was a deserialization issue on the server somewhere in the ReactFlight protocol.
And this patch also fixes a security vulnerability which is what we just talked about the big React problem that you know you can just fix by upgrading.
And let's take a look at the commit now.
For better or for worse, this commit is really long. This is actually not so bad
really long. This is actually not so bad because we don't want to provide the reproduction of the issue until literally everyone has upgraded. But I
need to admit I already took a careful look at this whole commit and I think the issue fix for the vulnerability might be this one. The import has own
property from shared has own property.
So basically before we returned the module exports at the index of metadata name which looks very similar to what I just showed you where you could access things on the object inheritance chain
above the module exports that usually users should not be allowed to access right like the constructor for example.
Now we are checking does the module exports object have the metadata at the index of name. Is it an actual property of the object? And that seems a lot more
safe. Now, was this the main patch for
safe. Now, was this the main patch for the security vulnerability? I don't
know. And it's totally fine to not know.
Now, if you upgrade to any of these versions in XJS or any newer version in React, you're good. You're fine. But you
should probably do that. I should
probably do that, too, man. I think
we're all affected by this cuz I like experimenting in the most modern versions. And turns out sometimes very
versions. And turns out sometimes very very critical security vulnerabilities happen.
Loading video analysis...