我该如何干净地用Java猴子修补功能?

时间:2018-10-23 09:31:05

标签: javascript

具有低级C /汇编程序设计背景,我想知道的一件事是,是否有可能在Javascript中绕行功能 ,即用我定义的功能替换它,然后调用原始代码,以添加其他代码或挂钩该功能。
我已经找到了示例,但是它们都不符合我的要求,干净,创建其他变量等

1 个答案:

答案 0 :(得分:1)

Javascript中的猴子修补程序在许多框架中都被大量使用,例如 zone.js 修补程序异步操作(针对角度)。

解决方案1:使用猴子修补的最简单方法如下。

var orig_setTimeout = window.setTimeout;

window.setTimeout = function setTimeout(fn, ms) {
    // your patching code goes here
    return orig_setTimeout(fn, ms);
}

解决方案2:使用 IIFE

信贷 @Annihil link

function originalFn(arg){
    return console.log("originalFn is invoked with argument: " + arg);
}

var patchedFn = (function(originalFunction) {

    return function(){
        console.log("patched function is invoked with arguments: " + arguments)
        return originalFunction.apply(this, arguments);
    }
}(originalFn))


patchedFn("Hello");

// Above invocation will results in 
patched function is invoked with arguments: Hello
originalFn is invoked with argument: Hello

解决方案3:,您可以使用 ES6代理

的应用陷阱
var patchedFn = {
  apply (target, ctx, args) {
    console.log("patched function is invoked with arguments: " + args)
    return Reflect.apply(...arguments)
  }
}
function originalFn (arg) {
    return console.log("originalFn is invoked with argument: " + arg);
}
var proxyFn = new Proxy(originalFn, patchedFn);

// Now proxy function can be invoked as following

proxyFn("Hello");
proxyFn(...["Hello"]);
proxyFn.call(null, "Hello");
proxyFn.apply(null, ["Hello"]);

// All the above invocation will print the below output

patched function is invoked with arguments: Hello
originalFn is invoked with argument: Hello

解决方案4::您还可以查看 ES6装饰器。它们也可能适合您的目的。有关ES6装饰器的介绍,请遵循sitepoint

案例研究: 如果您想了解 zone.js如何修补异步操作,请浏览博客文章monkey patching in zone.js