utils-extend CVE-2024-57077 · CVE-2020-8147
Prototype Pollution in utils-extend's deep extend.
The problem
utils-extend <= 1.0.8 (all published versions) is affected by
CVE-2024-57077, CVE-2020-8147 (CWE-1321 Prototype Pollution). The published package has
no fix available — exactly what npm audit reports. `utils-extend`'s deep `extend()` recursively merges a source object into a target. With no guard on reserved keys, a source object parsed from untrusted JSON containing `__proto__` causes the recursion to walk into and mutate `Object.prototype`, polluting every object in the process.
The fix — drop-in, no code changes
Add an overrides entry so every direct and transitive dependency on
utils-extend resolves to the patched fork, then reinstall:
{
"overrides": {
"utils-extend": "npm:@keep-lts/utils-extend@^1.0.9"
}
}
Equivalent for Yarn: use resolutions. The public API is unchanged — nothing else to do.
✓ Live on npm: @keep-lts/utils-extend · or install directly: npm i @keep-lts/utils-extend
What we changed
Source keys naming a prototype slot (`__proto__`, `constructor`, `prototype`) are skipped during the recursive merge. All legitimate deep-merge behavior — nested objects, arrays, and the multi-source `extend()` wrapper — is preserved.
Proof of concept (the vulnerability)
const u = require('utils-extend');
u.extend({}, JSON.parse('{"__proto__":{"polluted":"yes"}}'));
console.log(({}).polluted); // => 'yes'
@keep-lts/utils-extend@1.0.9How we keep it trustworthy
- Minimal, surgical patch — security only, no feature changes.
- A regression test that fails on the original and passes on the patch; legitimate behaviour preserved.
- Published under the
@keep-ltsorg with the full advisory and tests inside the package; upstream license & attribution retained.
Full advisory and changelog ship inside the package (SECURITY.md, CHANGELOG.md).