JavaScript原型污染指恶意修改Array.prototype等内置原型导致全局行为异常和安全漏洞,防御核心是不信任输入、禁用原型扩展、冻结关键原型、安全解析JSON并隔离不可信代码。

JavaScript 中内置原型(如 Array.prototype、Object.prototype、String.prototype 等)被意外或恶意修改,即“原型污染”,会导致全局行为异常、安全漏洞甚至远程代码执行。防御的核心原则是:**不信任外部输入、避免直接扩展内置原型、增强运行时防护**。
避免直接修改内置原型
这是最根本的预防措施。任何向 Array.prototype、Object.prototype 等添加方法或属性的操作,都可能破坏其他依赖原生行为的代码(包括第三方库)。
- ❌ 不要写:
Array.prototype.last = function() { return this[this.length - 1]; }; - ✅ 推荐替代方案:
- 使用工具函数:
const last = arr => arr[arr.length - 1]; - 使用类封装:
class MyArray extends Array { last() { return this[this.length - 1]; } } - 用静态方法:
const ArrayUtils = { last(arr) { return arr?.[arr.length - 1]; } };
- 使用工具函数:
校验并冻结关键原型对象
在应用启动早期(如入口文件顶部),可对高风险原型对象进行只读锁定,防止后续篡改。
- 对
Object.prototype冻结(需谨慎,仅限可信环境):if (Object.prototype.constructor === Object) { Object.freeze(Object.prototype); } - 更稳妥做法:冻结常用扩展点(如
Object、Array构造函数自身及其prototype):Object.freeze(Object); Object.freeze(Object.prototype);<br>Object.freeze(Array); Object.freeze(Array.prototype);
- ⚠️ 注意:
freeze无法递归冻结嵌套对象,且某些环境(如旧版 IE)不支持;建议配合 ESLint 规则(如no-extend-native)从开发阶段拦截。
安全合并与解析对象(尤其处理 JSON/用户输入)
原型污染常发生在深度合并(deep merge)、路径访问(如 obj[a][b][c])或 JSON 解析后未过滤的场景中。关键是要阻断 __proto__、constructor.prototype 等污染向量。
- 使用已验证的安全库:
lodash.merge(v4.17.21+ 默认防御__proto__)、fast-deep-equal或专用防护库如hoek(hapi 生态)。 - 手动防护示例(简易 deepAssign):
function safeAssign(target, source) {<br> for (const key in source) {<br> if (key === '__proto__' || key === 'constructor') continue;<br> if (typeof source[key] === 'object' && source[key] !== null && !Array.isArray(source[key])) {<br> target[key] = target[key] || {};<br> safeAssign(target[key], source[key]);<br> } else {<br> target[key] = source[key];<br> }<br> }<br> return target;<br>} - 解析用户 JSON 时,先用
JSON.parse(jsonStr, (k, v) => k === '__proto__' ? undefined : v)过滤关键词。
运行时监控与沙箱隔离(高级防护)
在敏感环境(如插件系统、低权限脚本执行)中,可主动检测原型是否被篡改,或在隔离上下文中运行不可信代码。
- 启动时快照关键属性:
const origHasOwnProperty = Object.prototype.hasOwnProperty;<br>if (Object.prototype.hasOwnProperty !== origHasOwnProperty) {<br> throw new Error('Object.prototype polluted!');<br>} - 使用
VM2或isolated-vm执行第三方脚本,天然隔离原型链。 - 在 Web Worker 或 iframe 中运行高风险逻辑,利用浏览器进程/上下文隔离机制。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











