Полноценно можно сделать только используя Proxy, но работать будет только в окружении ES-2015 (большинство актуальных браузеров уже поддерживают)
Не полноценно (зато будет работать в браузерах типа IE) - можно сделать через хак предложенный
0xD34F с возвратом своего объекта (функции) из конструктора
Пример с Proxy:
const TestClass = (function() {
class TestClass {
constructor() {
this.calls = '';
}
toString() {
return this.calls;
}
}
Object.setPrototypeOf(TestClass.prototype, Function.prototype);
function callTestClassInstance(el) {
this.calls += String(el);
}
return new Proxy(TestClass, {
construct(TestClass, args) {
const instance = new TestClass(...args);
const target = args => callTestClassInstance.apply(instance, args);
Object.setPrototypeOf(target, TestClass.prototype);
return new Proxy(target, {
apply(target, _, args) {
return target(args);
},
get(_, name) {
return instance[name];
},
set(_, name, value) {
instance[name] = value;
return true;
},
has(_, name) {
return name in instance;
},
deleteProperty(_, name) {
return delete instance[name];
},
defineProperty(_, name, descriptor) {
return Object.defineProperty(instance, name, descriptor);
},
getOwnPropertyDescriptor(_, name) {
return Object.getOwnPropertyDescriptor(instance, name);
},
ownKeys() {
return Object.getOwnPropertyNames(instance).concat(Object.getOwnPropertySymbols(instance));
}
});
}
});
})();