Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

fixes #1819: bound instance methods should reflect prototype changes

  • Loading branch information...
commit 662a67139740f5ef0ae6a64833e8d4641253670f 1 parent a6081ca
@michaelficarra authored
View
9 lib/coffee-script/nodes.js
@@ -1107,14 +1107,16 @@
};
Class.prototype.addBoundFunctions = function(o) {
- var bvar, lhs, _i, _len, _ref2, _results;
+ var bvar, lhs, method, _i, _len, _ref2, _results;
if (this.boundFuncs.length) {
_ref2 = this.boundFuncs;
_results = [];
for (_i = 0, _len = _ref2.length; _i < _len; _i++) {
bvar = _ref2[_i];
lhs = (new Value(new Literal("this"), [new Access(bvar)])).compile(o);
- _results.push(this.ctor.body.unshift(new Literal("" + lhs + " = " + (utility('bind')) + "(" + lhs + ", this)")));
+ method = bvar.compile(o);
+ method = IS_STRING.test(method) ? method : "\"" + method + "\"";
+ _results.push(this.ctor.body.unshift(new Literal("" + lhs + " = " + (utility('bindMethod')) + "(" + method + ", this)")));
}
return _results;
}
@@ -2431,6 +2433,9 @@
bind: function() {
return 'function(fn, me){ return function(){ return fn.apply(me, arguments); }; }';
},
+ bindMethod: function() {
+ return 'function(method, me){ var proto = me.constructor.prototype; return function(){ return proto[method].apply(me, arguments); }; }';
+ },
indexOf: function() {
return "Array.prototype.indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (" + (utility('hasProp')) + ".call(this, i) && this[i] === item) return i; } return -1; }";
},
View
8 src/nodes.coffee
@@ -846,7 +846,9 @@ exports.Class = class Class extends Base
if @boundFuncs.length
for bvar in @boundFuncs
lhs = (new Value (new Literal "this"), [new Access bvar]).compile o
- @ctor.body.unshift new Literal "#{lhs} = #{utility 'bind'}(#{lhs}, this)"
+ method = bvar.compile o
+ method = if IS_STRING.test method then method else "\"#{method}\""
+ @ctor.body.unshift new Literal "#{lhs} = #{utility 'bindMethod'}(#{method}, this)"
# Merge the properties from a top-level object as prototypal properties
# on the class.
@@ -1817,6 +1819,10 @@ UTILITIES =
function(fn, me){ return function(){ return fn.apply(me, arguments); }; }
'''
+ bindMethod: -> '''
+ function(method, me){ var proto = me.constructor.prototype; return function(){ return proto[method].apply(me, arguments); }; }
+ '''
+
# Discover if an item is in an array.
indexOf: -> """
Array.prototype.indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (#{utility 'hasProp'}.call(this, i) && this[i] === item) return i; } return -1; }
View
15 test/classes.coffee
@@ -527,3 +527,18 @@ test "#1598: super works for static methods too", ->
'pass? ' + super
eq Child.method(), 'pass? yes'
+
+test "#1819: bound instance methods should reflect prototype changes", ->
+ class C
+ a: => false
+ "b": => false
+ before = new C
+ ok not before.a()
+ ok not before.b()
+ C::a = -> true
+ C::b = => true
+ after = new C
+ ok before.a()
+ ok before.b()
+ ok after.a()
+ ok after.b()
Please sign in to comment.
Something went wrong with that request. Please try again.