如何在JavaScript中代理承诺es6

sam*_*sam 6 javascript proxy-classes es6-promise

我正在尝试在原生Firefox(并使用Babel)中代理承诺.

var prom = new Promise(function(resolve, reject){resolve(42)});
var promProxy = new Proxy(prom, {});
promProxy.then(function(response){console.log(response)});
Run Code Online (Sandbox Code Playgroud)

这不起作用,我得到'TypeError:'然后'调用一个没有实现接口Promise的对象.'

Tra*_*man 7

您需要让您的处理程序实现get()陷阱并返回绑定版本prom.then

var prom = new Promise(function(resolve, reject){resolve(42)});
var promProxy = new Proxy(prom, {
  get: function(target, prop) {
    if (prop === 'then') {
      return target.then.bind(target);
    }
  }
});
promProxy.then(function(response){console.log(response)});
Run Code Online (Sandbox Code Playgroud)

请注意,如果您只想代理所有访问器,则该get函数将如下所示:

var promProxy = new Proxy(prom, {
  get: function(target, prop) {
    var value = target[prop];
    return typeof value == 'function' ? value.bind(target) : value;
  }
});
Run Code Online (Sandbox Code Playgroud)

bind 将确保在处理诸如Promises或控制台之类的Native对象时不会错误地调用该函数.

编辑:在某些情况下,浏览器/节点将有一个过时版本的代理,在这种情况下,您将需要使用和谐反射来使其更新.


Jef*_*ard 6

嗯,这个问题是How to Proxy a Promise。我来到这里寻找如何承诺代理- 或者更准确地说,如何解析代理。我怀疑其他人也可能会登陆这里,所以我会将其发布在这里,以防万一。

我已经有了一个很好的工作代理对象,然后我尝试将它包装在一个承诺中:

var p = new Promise(function(resolve, reject) {
  var proxy = get_my_proxy();
  resolve(proxy);
});
Run Code Online (Sandbox Code Playgroud)

你难道不知道吗,然后该死的解析方法会向我的代理询问一个then属性(这是我的代理逻辑意外的,导致它抛出)。它可能并不理想,具体取决于您的代理的用途,但这是我解决此问题的方法(并且足够适当,因为我的问题是这个问题的反面,我的解决方案也是反面的) - 通过null返回then- - 从而让我resolve()知道我没有通过Promise(又名Thenable)。

get: function(target, prop) {
  if (prop === 'then') return null; // I'm not a Thenable
  // ...the rest of my logic
}
Run Code Online (Sandbox Code Playgroud)