我正在测试我的应用程序,我有一个依赖注入系统就像这样(我在这里粘贴一个非常简化的版本)
test.start = function(callback) {
// do stuff;
load(callback);
}
function load(callback) {
var args = ...// read callback's arguments
// args = ['moduleA', 'moduleB'];
var injectedArgs = args.map(function(a) {
return require('./lib/' + a);
});
// call function with deps injected
callback.apply(null, injectedArgs);
}
// test.js
test.start(function(moduleA, moduleB) {
moduleA.functionA();
moduleB.functionB();
});
我需要做的是在调用回调并开始测试之前的异步作业,在这种特殊情况下,这将是
test.start = function(callback) {
// do stuff;
load(function(moduleA, moduleB, moduleC) {
moduleC.resetData(function() {
return callback(moduleA, moduleB);
})
});
}
我需要使这个动态,对于所有具有不同模块作为其回调参数的测试。 要求是
load
所以基本上我需要创建添加moduleC
参数的中间函数,运行resetData
函数并调用原始回调。
我可以使用构建动态扩展的参数列表
var fn = new Function(newArgumentList, /*function body*/)
但我无法附加正确的函数体(使用字符串),因为我丢失了原始的回调上下文。
更新
DI库是modularity,它读取回调定义以获取依赖性。所以基本上,给定回调function(foo, bar) { ... }
我需要创建一个新的function(foo, bar, db) { db.resetData(function() { return callback(foo, bar) } )}
答案 0 :(得分:1)
如果load
本身就是你可以改变的东西(例如,不是测试定义的一部分),你会很高兴知道这很容易做到:你使用{{1} }:
Function#apply
如果您可以更新 function load(callback) {
var origCallback;
if (/*flag saying you need to do this*/) {
origCallback = callback;
callback = function() {
/*...do your injected work here...*/
return origCallback.apply(this, arguments); // `arguments` looks like pseudo-code, but it isn't; it's an identifier created in the function's scope (for non-arrow functions)
};
}
var args = ...// read callback's arguments
// args = ['moduleA', 'moduleB'];
var injectedArgs = args.map(function(a) {
return require('./lib/' + a);
});
// call function with deps injected
callback.apply(null, injectedArgs);
}
符号以使其指向新功能,您甚至可以更改load
。< / p>
load
如果你很好奇,是的,你可以更新函数声明创建的符号(是的,每个规范的符号,而不是&#34;棘手&#34;)。例如,这是完全有效的:
var oldload = load;
load = function() {
/*...do your reset work here...*/
return oldload.apply(this, arguments);
};
示例:强>
function foo() {
console.log("I'm foo");
}
var oldFoo = foo;
foo = function() {
console.log("I'm the new foo");
return oldFoo.apply(this, arguments);
};
foo(); // "I'm the new foo", then "I'm foo"
&#13;
function foo() {
snippet.log("I'm foo");
}
var oldFoo = foo;
foo = function() {
snippet.log("I'm the new foo");
return oldFoo.apply(this, arguments);
};
foo(); // "I'm the new foo", then "I'm foo"
&#13;
答案 1 :(得分:0)
我最后找到了解决方案。 由于模块化支持类似角度的注入
['modules/a', 'modules/b', function(moduleA, moduleB) {
// use modules here
}]
我可以像这样编写自定义回调
var customCallback = function() {
var args = Array.prototype.slice.call(arguments);
var injectedDBModule = args.pop();
injectedDBModule.resetData(function() {
// call the original callback function
return originalCallback.apply(null, args);
}
}
var loadCallback = originalInjectedModules; // ['moduleA', 'moduleB']
loadCallback.push('db');
loadCallback.push(customCallback);
modularity.load(loadCallback);