Skip to content
This repository was archived by the owner on Apr 12, 2024. It is now read-only.

Commit a27d827

Browse files
committed
fix($compile): get $$observe listeners array as own property
Prevent accidentally treating a builtin function from Object.prototype as the binding object, and thus preventing the compiler from throwing when using attribute binding names which match a property of the Object prototype. Closes #9343 Closes #9345
1 parent a1648a7 commit a27d827

File tree

2 files changed

+30
-1
lines changed

2 files changed

+30
-1
lines changed

src/ng/compile.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -929,7 +929,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
929929
*/
930930
$observe: function(key, fn) {
931931
var attrs = this,
932-
$$observers = (attrs.$$observers || (attrs.$$observers = {})),
932+
$$observers = (attrs.$$observers || (attrs.$$observers = Object.create(null))),
933933
listeners = ($$observers[key] || ($$observers[key] = []));
934934

935935
listeners.push(fn);

test/ng/compileSpec.js

+29
Original file line numberDiff line numberDiff line change
@@ -3124,6 +3124,35 @@ describe('$compile', function() {
31243124
}));
31253125

31263126

3127+
it('should be able to bind attribute names which are present in Object.prototype', function() {
3128+
module(function() {
3129+
directive('inProtoAttr', valueFn({
3130+
scope: {
3131+
'constructor': '@',
3132+
'toString': '&',
3133+
3134+
// Spidermonkey extension, may be obsolete in the future
3135+
'watch': '=',
3136+
}
3137+
}));
3138+
});
3139+
inject(function($rootScope) {
3140+
expect(function() {
3141+
compile('<div in-proto-attr constructor="hello, world" watch="[]" ' +
3142+
'to-string="value = !value"></div>');
3143+
}).not.toThrow();
3144+
var isolateScope = element.isolateScope();
3145+
3146+
expect(typeof isolateScope.constructor).toBe('string');
3147+
expect(isArray(isolateScope.watch)).toBe(true);
3148+
expect(typeof isolateScope.toString).toBe('function');
3149+
expect($rootScope.value).toBeUndefined();
3150+
isolateScope.toString();
3151+
expect($rootScope.value).toBe(true);
3152+
});
3153+
});
3154+
3155+
31273156
describe('bind-once', function () {
31283157

31293158
function countWatches(scope) {

0 commit comments

Comments
 (0)