__proto__
一个Foo类实例化出来的foo对象,可以通过foo.__proto__
属性来访问Foo类的原型,也就是说:
foo.__proto__= Foo.prototype 对象 构造函数
所以,总结一下:
-
prototype
是一个类的属性,所有类对象在实例化的时候将会拥有prototype
中的属性和方法 -
一个对象的
__proto__
属性,指向这个对象所在的类的prototype
属性 -
每个构造函数(constructor)都有一个原型对象(prototype)
-
对象的
__proto__
属性,指向类的原型对象prototype
-
JavaScript使用prototype链实现继承机制
原型链污染是什么
之前说到foo.__proto__
指向的是Foo
类的prototype
。那么,如果我们修改了foo.__proto__
中的值,是不是就可以修改Foo类呢?
做个简单的实验:
最后,虽然zoo是一个空对象{},但zoo.bar
的结果居然是2
原因也显而易见:因为前面我们修改了foo的原型foo.__proto__.bar = 2
,而foo是一个Object类的实例,所以实际上是修改了Object这个类,给这个类增加了一个属性bar,值为2。
后来,我们又用Object类创建了一个zoo对象let zoo = {}
,zoo对象自然也有一个bar属性了。
那么,在一个应用中,如果攻击者控制并修改了一个对象的原型,那么将可以影响所有和这个对象来自同一个类、父祖类的对象。这种攻击方式就是原型链污染。
mess.js
attach.html