Javascript 如何将函数链接与异步函数一起使用?
我目前正在编写一个e2e测试,我想创建一些类来为我抽象某些异步任务。最后,我想实例化一个对象,让我来链接异步函数。假设我有一个Javascript 如何将函数链接与异步函数一起使用?,javascript,class,object,asynchronous,async-await,Javascript,Class,Object,Asynchronous,Async Await,我目前正在编写一个e2e测试,我想创建一些类来为我抽象某些异步任务。最后,我想实例化一个对象,让我来链接异步函数。假设我有一个Walker,让我在页面中导航。我想这样使用它: const walker=新walker(t) 等待步行者 .goToMainPage() .goToProfile() 目前我只能这样使用它: const walker=新walker(t) wait walker.goToMainPage() wait walker.goToProfile() 这是我目前如何实现W
Walker
,让我在页面中导航。我想这样使用它:
const walker=新walker(t)
等待步行者
.goToMainPage()
.goToProfile()
目前我只能这样使用它:
const walker=新walker(t)
wait walker.goToMainPage()
wait walker.goToProfile()
这是我目前如何实现Walker类的一个粗略实现。其中t
是一个对象,允许我在浏览器中执行异步操作
class Walker{
建造师(t){
t=t;
}
异步goToMainPage(){
等待t.goTo('url/main')
还这个
}
异步goToProfile(){
等待t.goTo('url/Profile')
还这个
}
}
有没有关于如何创建异步可链接函数调用的想法?您使用的是
async/await
——它本质上是承诺链接的替代品(承诺本身就是回调地狱的解决方案)。如果您真的想使用链接:
walker().then(w => w.goToMainPage()).then(w => w.goToProfile());
await
不仅适用于承诺,而且适用于提供处理程序的每个对象。。。因此,您的Walker可以实现一个。然后方法来允许等待:
class Walker {
constructor(t) {
this.t = t;
// set up a task queue for chaining
this.task = Promise.resolve();
}
// shedules a callback into the task queue
doTask(cb) {
// TODO: error handling
return this.task = this.task.then(cb);
}
// allows to use this like a promise, e.g. "await walker";
then(cb) { cb(this.task); }
goToMainPage () {
this.doTask(async () => { // shedule to chain
await t.goTo('url/main')
});
return this; // return walker for chaining
}
}
这允许您执行以下操作:
await walker.goToMainPage();
await walker.goToMainPage().goToMainPage();
如果您从doTask
内部返回某个内容,wait
ing将解析为:
returnStuff() {
this.doTask(() => "stuff");
return this;
}
//...
console.log(await walker.returnStuff()); // "stuff"
console.log(await walker.returnStuff().goToMainPage()); // undefined, result gets lost
我确实明白了,但我想使用上面提到的语法。我知道,如果以某种方式构建对象/类,就有可能获得这种语法。我目前使用的e2e测试库(Testcafe)允许使用这种语法。因此,必须有一种方法来实现这种对象结构。这是一个非常简洁的解决方案。基本上,我们将所有承诺委托给其他人,直到某个代码调用我们的。然后处理程序。对于OP的示例代码,.then()
将由wait
调用。整洁的我在代码笔中尝试了这段代码,然后返回这段代码
仅返回Walker{t:undefined}
,只返回t
,不返回两个方法goToMainPage
和goToProfile
。我对此有点困惑。为什么方法不是实例化类的一部分?有人能解释吗?杰里米,因为他们是原型的一部分Walker{…}
告诉您有关继承的信息…@JeremyThille应该正常工作的不是代码,更像sudo代码。我稍微更新了这个例子。在类的实例化过程中,我们需要传递t
对象,例如newwalker(t)
。t来自我正在使用的另一个库。你可以把它想象成一个对象,它提供了一系列异步功能。@Jonaswillms那么,类的方法只是原型的一部分,而不是类本身的一部分吗?那是weird@jeremy嗯new Walker
仍然是一个实例,这就是这个
所指向的。是的,只有static
方法是构造函数本身的一部分,方法是原型的一部分。记住:类
只是构造器周围的语法糖。