Javascript (ECMA-6) class magic method __call like PHP
There are no special __methods()
in Javascript like in PHP, so all you have are those getters
, setters
, toString()
and valueOf()
.
You could give Object.defineProperty()
a shot, because with that you can dynamically create getters like so:
Object.defineProperty(obj, 'first_name', {
get: function () { return … }
});
mdn
The result is similar to:
var obj = {
get first_name () { return … }
}
If you need to call method of an object, you can also do it like that:
var prop = 'getFirstName',
result = obj[prop]();
What also can be done in a for
loop.
You can use a proxy to detect access to a property that your object does not have, and deal with it -- this comes close to PHP's __call
:
var person = new Person();
// Wrap the object in a proxy
var person = new Proxy(person, {
get: function(person, field) {
if (field in person) return person[field]; // normal case
console.log("Access to non-existent property '" + field + "'");
// Check some particular cases:
if (field == 'first_name') return person.getFirstName;
// ...
// Or other cases:
return function () {
// This function will be executed when property is accessed as a function
}
}
});
You could even do this in the constructor of your class:
class Person {
constructor(data) {
this.init(data);
return new Proxy(this, {
get: function(person, field) {
if (field in person) return person[field]; // normal case
console.log("Access to non-existent property '" + field + "'");
// Check some particular cases:
if (field == 'first_name') return person.getFirstName;
// ...
// Or other cases:
return function () {
// This function will be executed when property is accessed as a function
return 15; // example
}
}
});
}
// other methods ...
//
}
The nice thing about proxies is that the returned object is still considered an instance of the original class. With the above code, the following will be true:
new Person() instanceof Person