CVE-2026-54737
JavaScript vulnerability analysis and mitigation

Overview

CVE-2026-54737 is a prototype pollution vulnerability in the npm package @phun-ky/defaults-deep, a lodash-free deep merge utility. Prior to version 2.0.5, the library's defaultsDeep() function recursively merged user-supplied objects without filtering unsafe property names (__proto__, constructor, and prototype), allowing writes to Object.prototype. The vulnerability was discovered by researcher supeRdaem, fixed on June 8, 2026, and publicly disclosed via GitHub Advisory on June 9, 2026, with the advisory published to the GitHub Advisory Database on July 31, 2026. It carries a CVSS v3.1 base score of 7.3 (High) (Github Advisory, Feedly).

Technical details

The root cause is classified as CWE-1321 (Improperly Controlled Modification of Object Prototype Attributes — 'Prototype Pollution'). The internal mergeWith / baseMerge function iterated over all own keys of a source object, including __proto__, constructor, and prototype, without any filtering. When a crafted object such as JSON.parse('{"__proto__":{"polluted":"yes"}}') was passed to defaultsDeep(), the recursive merge would write attacker-controlled properties directly onto Object.prototype, poisoning the prototype chain for all objects in the Node.js process. The fix introduced a constant UNSAFE_KEYS set ({'__proto__', 'constructor', 'prototype'}) and skips any key matching this set at every level of recursion (Github Advisory, Fix Commit).

Impact

Successful exploitation allows an unauthenticated remote attacker to pollute Object.prototype within the affected Node.js process, causing all subsequently created objects to inherit attacker-controlled properties. Depending on application logic, this can result in logic bypasses (e.g., privilege escalation by injecting properties checked for authorization), denial of service through unexpected behavior or crashes, or limited information disclosure — corresponding to low confidentiality, integrity, and availability impacts per the CVSS scoring. The blast radius is process-wide: any code in the same runtime that relies on object property checks may be affected (Github Advisory).

Exploitation steps

  1. Identify target: Determine that the target Node.js application uses @phun-ky/defaults-deep version < 2.0.5 and passes user-controlled input to defaultsDeep() or mergeWith().
  2. Craft malicious payload: Construct a prototype pollution payload, e.g., via JSON.parse('{"__proto__":{"isAdmin":true}}') or { constructor: { prototype: { isAdmin: true } } }.
  3. Deliver payload: Submit the crafted object as input to any application endpoint that feeds user-supplied data into defaultsDeep() — for example, a JSON body in an HTTP request that is merged with default configuration.
  4. Trigger pollution: The unpatched baseMerge function processes the __proto__ or constructor key without filtering, writing isAdmin: true (or any attacker-chosen property) onto Object.prototype.
  5. Exploit polluted prototype: Subsequent code in the same process that checks obj.isAdmin on a plain object will now evaluate to true even for objects that never had that property set, potentially bypassing authorization checks or altering application behavior (Github Advisory, Fix Commit).

Indicators of compromise

  • Logs: Unexpected authorization grants or privilege escalation events in application logs following receipt of JSON payloads containing __proto__, constructor, or prototype keys; HTTP request logs showing POST bodies with these keys.
  • Network: Inbound HTTP requests with JSON bodies containing "__proto__", "constructor", or "prototype" as top-level or nested keys directed at endpoints that perform object merging.
  • Process Behavior: Unexpected truthy values for properties on plain objects ({}) that were never explicitly set; application logic behaving as if all objects share unexpected properties (e.g., isAdmin, polluted) — detectable via runtime assertions or monitoring frameworks.
  • File System: No specific file artifacts are expected from prototype pollution alone, but secondary payloads (e.g., written files, spawned processes) may appear if the pollution is chained with other application logic.

Mitigation and workarounds

Upgrade @phun-ky/defaults-deep to version 2.0.5 or later, which blocks unsafe keys (__proto__, constructor, prototype) at all levels of recursion during merge operations (Release 2.0.5). For teams unable to upgrade immediately, sanitize all untrusted input before passing it to defaultsDeep() by recursively removing or rejecting any keys named __proto__, constructor, or prototype. Additionally, consider using Object.freeze(Object.prototype) in non-production environments to detect pollution attempts early during testing (Github Advisory).

Additional resources


SourceThis report was generated using AI

Related JavaScript vulnerabilities:

CVE ID

Severity

Score

Technologies

Component name

CISA KEV exploit

Has fix

Published date

CVE-2026-55100HIGH8.7
  • JavaScript logoJavaScript
  • hashi-vault-js
NoYesJul 31, 2026
CVE-2026-54729HIGH8.7
  • JavaScript logoJavaScript
  • dssrf
NoYesJul 31, 2026
CVE-2026-54737HIGH7.3
  • JavaScript logoJavaScript
  • @phun-ky/defaults-deep
NoYesJul 31, 2026
CVE-2026-62324MEDIUM5.4
  • JavaScript logoJavaScript
  • jodit
NoYesJul 31, 2026
CVE-2026-65841MEDIUM5.3
  • JavaScript logoJavaScript
  • jodit
NoYesJul 31, 2026

Free Vulnerability Assessment

Benchmark your Cloud Security Posture

Evaluate your cloud security practices across 9 security domains to benchmark your risk level and identify gaps in your defenses.

Request assessment

Get a personalized demo

Ready to see Wiz in action?

"Best User Experience I have ever seen, provides full visibility to cloud workloads."
David EstlickCISO
"Wiz provides a single pane of glass to see what is going on in our cloud environments."
Adam FletcherChief Security Officer
"We know that if Wiz identifies something as critical, it actually is."
Greg PoniatowskiHead of Threat and Vulnerability Management