2016-10-14 12 views
0

Мне нужно перехватить вызовы на некоторые функции API DOM и сохранить их аргументы в качестве побочного эффекта. Например, предположим, что меня интересуют функции getElementsByTagName и getElementById. Смотрите пример ниже:Перехват вызовов в функции DOM API

"use strict"; 
const jsdom = require("jsdom"); 
let document = jsdom.jsdom("<html><head></head><body><div id='foo'><div></div></div></body></html>"); 
let cpool = {ids: [], tags: []}; 
let obj = document.getElementById("foo"); 
// --> cpool = {ids: ["foo"], tags: []} 
obj.getElementsByTagName("div"); 
// --> cpool = {ids: ["foo"], tags: ["div"]} 

Один важное замечание в том, что я использую node.js и document объект реализуется jsdom библиотеки. До сих пор я пытался использовать ES6 Proxies для изменения поведения вышеупомянутых функций DOM.

Вот как я пытался проксировать объект документ объект, чтобы уловить все вызовы методов. Интересно, как и как с помощью этой техники или какой-то другой я могу найти решение моей проблемы.

let documentProxy = new Proxy(document, { 
    get(target, propKey, receiver) { 
     return function (...args) { 
      Reflect.apply(target, propKey, args); 
      console.log(propKey + JSON.stringify(args)); 
      return result; 
     }; 
    } 
});  
documentProxy.getElementById("foo"); 
// --> getElementById["foo"] 
+0

Я не знаю, почему, но это звучит, как вы делаете плохо ... – evolutionxbox

+0

@evolutionxbox что вы имеете в виду 'плохой thing'? –

+0

Какова ваша [фактическая проблема] (http://meta.stackexchange.com/q/66377), которую вы пытаетесь решить, перехватив эти вызовы? – Bergi

ответ

0

Если вы хотите перехватить только вызовы этих двух функций, вам не нужно использовать прокси. Вы можете просто сохранить копию исходной функции и переопределить функцию, которой вы хотите перехватить вызовы, с функцией, которая сохраняет аргументы, а затем вызывает исходную функцию.

const cpool = {ids: [], tags: []} 
 

 
;(getElementsByTagNameCopy => { 
 
    document.getElementsByTagName = tag => { 
 
    cpool.tags.push(tag) 
 
    return Reflect.apply(getElementsByTagNameCopy, document, [tag]) 
 
    } 
 
})(document.getElementsByTagName) 
 

 
;(getElementsByTagNameCopy => { 
 
    Element.prototype.getElementsByTagName = function(tag) { 
 
    cpool.tags.push(tag) 
 
    return Reflect.apply(getElementsByTagNameCopy, this, [tag]) 
 
    } 
 
})(Element.prototype.getElementsByTagName) 
 

 
;(getElementByIdCopy => { 
 
    document.getElementById = id => { 
 
    cpool.ids.push(id) 
 
    return Reflect.apply(getElementByIdCopy, document, [id]) 
 
    } 
 
})(document.getElementById) 
 

 
console.log(document.getElementsByTagName('body')) 
 
console.log(document.getElementById('whatever')) 
 
console.log(document.body.getElementsByTagName('div')) 
 
console.log(cpool)

+0

Он отслеживает только вызовы объекта документа, а не _Element_. Например, здесь 'console.log (document.getElementById ('test'). GetElementsByTagName ('span'));' _span_ не сохраняется среди тегов. –

+0

@AlexElyasov См. Мое редактирование. –

+0

представляется неприемлемым для перезаписывания каждого индивидуального метода; просто говорю. – naomik

 Смежные вопросы

  • Нет связанных вопросов^_^