When you replace the object on a function's prototype property, you have to take responsibility for fixing up the constructor property on it:
foo.prototype = {
constructor: foo, // <====
getUppercase: function() {
return this.text.toUpperCase();
}
};
It's not automatic. The only automatic population of that property is on the default object assigned to the function's prototype property when the function is originally created.
function foo(text){
this.text = text;
}
foo.prototype = {
constructor: foo,
getUppercase: function() {
return this.text.toUpperCase();
}
};
var bar = new foo("bar");
console.log(bar.constructor.name);
Alternately, don't replace the default object on prototype, just augment it (usually my preference):
foo.prototype.getUppercase = function() {
return this.text.toUpperCase();
};
You can do multiple of those via Object.defineProperties or Object.assign (that latter may need a shim) or your own utility function.
Finally, I'd be remiss if I didn't call out a couple of things:
Overwhelmingly, constructor function names start with a capital letter in JavaScript. It is just a convention, but it's a very, very well-established convention.
In ES2015+, you can use class for a more concise version:
Function#name is new as of ES2015 and support is a bit sketchy as I write this in July 2016. (Chrome 51+ does indeed have it.)
FWIW:
class Foo {
constructor(text) {
this.text = text;
}
getUppercase(){
return this.text.toUpperCase();
}
}
var bar = new Foo("bar");
console.log(bar.constructor.name);
Of course, if you need to support older engines (like IE11), you need to transpile if you do that... (But then again, if you're using Function#name, that's from ES2015 too.)
bar instanceof foowill returntrue. This may be a helpful alternative if checking the constructor's actual name isn't a hard requirement in this scenario.