arrays - NodeJS将顺序函数调用转换为函数数组
问题描述
我有一个函数以线性方式回调类中的其他函数。
async runTask() {
debug('runTask');
debug(this.taskData);
try {
// Short circuit for testing
if (process.env.TASKTIMER) {
return setTimeout(() => {
this.taskComplete();
}, process.env.TASKTIMER);
}
// Setup project folder & Git Clone
await this.pullPackageWait();
// Create input and output directory
await this.mkIODirWait();
// Store task data as json
await this.writeTaskDataJSONWait();
// Download Inputs From Amazon
await this.downloadInputsWait();
// Link Input files
await this.linkInputsWait();
// Download Resources From Amazon
await this.downloadResourcesWait();
// Relax permission on tmp directory
await this.chmodTaskDir();
// Destroys the job after timeout
await this.jobTimeout();
// Determine Handler
console.log(this.taskData.handler);
await this.initHandler();
await this._handler.startJob();
} catch (err) {
this.logger.error(err);
return this.taskError();
}
我正在尝试将函数调用转换为this answer之后的函数数组。重构后我的函数如下所示:
async runTask() {
debug('runTask');
debug(this.taskData);
try {
// Short circuit for testing
if (process.env.TASKTIMER) {
return setTimeout(() => {
this.taskComplete();
}, process.env.TASKTIMER);
}
let currentFunction = 0;
const functionsToRun = [
this.pullPackageWait,
this.mkIODirWait,
this.writeTaskDataJSONWait,
this.downloadInputsWait,
this.linkInputsWait,
this.downloadResourcesWait,
this.chmodTaskDir,
this.jobTimeout,
];
debug('Before The Loop');
for (currentFunction; currentFunction < functionsToRun.length; currentFunction++) {
debug('In The Loop');
await functionsToRun[currentFunction]();
console.log('Writing to the file');
await this.writeState();
}
// Determine Handler
console.log(this.taskData.handler);
await this.initHandler();
await this._handler.startJob();
} catch (err) {
this.logger.error(err);
return this.taskError();
}
使用原始代码,整个程序运行正常,但转换后它似乎在第一次回调时中断。我在转换的某个地方犯了错误吗?
解决方案
重构代码中最可能的错误来源是不正确的this
绑定。请注意以下事项:
this.foo();
不一样:
let foo = this.foo;
foo();
调用时里面this.foo()
的this
值foo()
会this
和this.foo
. 当调用内部foo()
的this
值时,foo()
将要么是全局对象,要么是undefined
全局对象,这取决于您是否启用了严格模式。
有关如何this
工作的完整解释,请参阅我对另一个问题的回答:Javascript 中的“this”关键字如何在对象文字中起作用?
TLDR
解决方案是将函数名称存储为字符串:
const functionsToRun = [
'pullPackageWait',
'mkIODirWait',
'writeTaskDataJSONWait',
'downloadInputsWait',
'linkInputsWait',
'downloadResourcesWait',
'chmodTaskDir',
'jobTimeout',
];
然后调用每个函数:
await this[functionsToRun[index]]();
或.bind()
功能:
const functionsToRun = [
this.pullPackageWait.bind(this),
this.mkIODirWait.bind(this),
this.writeTaskDataJSONWait.bind(this),
this.downloadInputsWait.bind(this),
this.linkInputsWait.bind(this),
this.downloadResourcesWait.bind(this),
this.chmodTaskDir.bind(this),
this.jobTimeout.bind(this),
];
并以您当前的方式称呼他们:
await functionsToRun[currentFunction]();
推荐阅读
- php - 在 Ubuntu 上使用 PhpStorm 进行 Xdebug
- python - 使用 Python 比较 2 个 CSV 文件
- javascript - 啊,啪!尝试使用 Fabric JS 在移动设备中加载大画布时的屏幕
- django - Django 多项选择字段数据在 POST 数据和表单数据中有所不同
- java - 在android应用程序中测试谷歌订阅不起作用
- string - Bash 字符串参数打印有不必要的撇号
- api - 将纬度和经度值作为变量传递时,在 REST API 中出现 BAD 请求错误
- php - 按 id 和总和合并数组
- django - 在 django_tenant 后端运行 APScheduler 任务不起作用
- python - Unittest python csv文件打开测试返回空列表