我们可以像Prisma库一样链接到Promise吗?

问题描述 投票:1回答:2

我正在寻找链式承诺的可能解决方案,如下所示。

const getDetailsFromDb = await prisma.someTableNames().field()

因为我知道的唯一可能的方法如下:

const SomethingToBeChained = function() {
   // where every method of object attached
   // to this instance should return this itself
   // so other properties attached to it can be accecd.
   return this
}
SomethingToBeChained.prototype = {
   methodOne: function () { ...do something...; return this }
   methodTwo: function () { ...do something...; return this }
}

// now one can do following.
SomethingToBeChained.methodOne().methodTwo()

但是,prisma客户可以同时做这两个事情?谁能解释一下prisma客户端背后的工作原理。它的结构如何实现同时调用await和chain对象?

我只知道这种方式?

const somethingAwaited = (await SomethingToBeChainedIsPromise().wantToChainSomethingButCant()) <--- Ugly
const wantThis = await SomethingToBeChainedIsPromise().wantToChainSomethingButCant()
javascript node.js
2个回答
0
投票

await可以与thenable一起使用;它不一定必须是本机Promise类/构造函数的实例。

所以您可以想象您的原型也有then方法:

SomethingToBeChained.prototype = {
   then: function (onFulfil, onReject) {
        // Here you could await some asynchronous database event
        // Once that comes back with success, call the onFulfil callback:
        setTimeout(onFulfil, 1000); 
   },
   methodOne: function () { ...do something...; return this },
   methodTwo: function () { ...do something...; return this }
}

有了这个扩展名,您可以神奇地使用await(它实际上将使用内部回调参数调用then方法)。一点模拟演示:

let obj = {
     then(cb) {
         setTimeout(cb, 1000);
     }
}

async function test() {
    console.log("before");
    await obj;
    console.log("after");
}

test();

您甚至可以使其与实际的Promise对象一起使用。在这种情况下,您的this对象应该是Promise类的实例,并使用您自己的方法进行了扩展。但是想法还是一样。


0
投票

我认为,解决此问题的最佳方法是让每个方法排队的动作稍后发送。换句话说,调用方法等同于声明要在以后执行的功能组合管道。

您的调用代码将需要进行一些更改:

var wantThis = await somethingToBeChained().somethingElse().start()

在这种情况下,除了start()方法以外,所有方法都返回this,该方法实际上应用了实函数并返回了promise。

这类似于创建异步函数合成管道:

const asyncPipe = (...fns) => x => fns.reduce(async (y, f) => f(await y), x);

这将产生一个事实之后可以调用的函数,以触发函数管道的实际应用。从功能应用程序中分离功能组成具有诸如更好的可测试性,更好的模块化和更容易调试的好处。

© www.soinside.com 2019 - 2024. All rights reserved.