Переопределение констуктора объектов
Всем привет. В одном из давних рецептов нашёл вот такой хак. Смысл его в переопределении ф-ции создания объектов
function Object() { console.log('we are here'); } var a = [{a: 1}]; Подразумевалось что при выполнении последней строки в консоль упадёт "we are here". Теперь же во всех браузерах надпись появляется только при таком вызове: var a = new Object() Существует ли сейчас какой-нибудь способ сделать это для всех создаваемых объектов ({a: 1}, [{a: 1}], new ...)? |
Единственный способ сделать это — создать ссылки на каждый созданный экземпляр. Вы не можете получить к ним доступ, не создавая такой механизм заранее.
let references = new Set(); let a, b, c; references.add(a = { a: 1 }); references.add(b = [1, 2, 3]); references.add(c = new Uint8Array(16)); // теперь есть ссылки на необходимые объекты console.log(references); a, b и c из примера выше не несут смысловой нагрузки, ведь если объект создан, то он где-нибудь используется... если только это не анонимный объект, который, например, сразу передаётся в качестве аргумента какой-либо функции. let references = new Set(); function $(object) { references.add(object); return object; } Object.defineProperty($, "references", { get() { return references; } }); // это можно оформить как отдельный модуль // export default $; ////////////////////////////////////////// $([1, 2, 3]); $({ a: 1 }); $(new Uint8Array(16)); // теперь есть ссылки на необходимые объекты console.log($.references); Другой способ (я предполагаю, что вы не можете этого сделать) — перехватить все действия по созданию объектов (используя контейнерный подход Proxy, с литералами не будет работать, см. ниже) и сохранить список всех объектов в вашем приложении... При выполнении {} не вызывается конструктор Object. Как описано в спецификации ECMA-262, пункт 12.2.6.7, вызывается абстрактная функция ObjectCreate с аргументом proto, который будет внутренним свойством [[Prototype]] для новосозданного объекта. Т. е. выполненный {} представляет из себя такой же объект, который возвращается при выполнении Object.create(Object.prototype); и представляет из себя { __proto__: Object.prototype } При вызове new Object() вызывается та же абстрактная функция ObjectCreate, и выполненный new Object() представляет из себя { __proto__: Object.prototype } Во время выполнения литералов массива, рег. выражения и т. д. соответствующий конструктор не вызывается, вызываютя определённые абстрактные функций, в результате выполнения которых получается, в случае литерала регулярного выражения, объект типа RegExp, который представляет из себя объект { __proto__: RegExp.prototype, lastIndex: 0 } с внутренними свойствами [[RegExpMatcher]], [[OriginalSource]] и [[OriginalFlags]]. Такой же объект получился бы при вызове new RegExp(); У классов типа Array, RegExp, Set и т. д. в определении конструктора нет вызовов конструктора родителя Object, хотя они и наследуют от него. |
Спасибо! Ответ очень поможет в моих поисках!
|
Часовой пояс GMT +3, время: 08:53. |