javascript - 通过一系列 promise (JS 继承/接口(interface))编译结果

标签 javascript jquery ajax promise

我正在构建一个“存储提供程序”,允许使用代码通过接口(interface)存储内容。将下面的代码片段视为伪代码,因为我要使用 MCVE。我正在尝试获取下面的 IMPORTANTDATAIMPORTANTKEY

在最低级别,我有一个baseService:

define([], function(){
    return function(){
        this.sendRequest = function(data){
              return $.ajax(data).done(function(response){
                  return response.IMPORTANTDATA; //          <---- This is needed
              }).fail(function(response){
                  throw new Error(response);
              }); 
        }
    }
})

我用它构建服务以重用一些基本功能,例如 - eventService:

define(["baseService"], function(baseService){
      const eventService = new baseService();
      eventService.postMediaEvent = function(eventType, mediaPath, storageProvider){
           // isolated logic here
           return eventService.sendRequest(someData);
      }
})

这就是事情开始变得棘手的地方:我有一个 baseStorageClient:

define(["eventService"], function (eventService) {
     return function(){
          this.storageProvider = null;
          const self = this;
          this.storeMetadata = function(eventType, mediaPath){
              return eventService.postMediaEvent(eventType, mediaPath, self.storageProvider);
          };

          this.storeMedia = function(){
              throw new Error("Not Implemented");
          };
     }
}

但是这个家伙从来没有被直接使用过。我创建了此实例 - 例如,indexedDbClient:

define(["baseStorageClient"], function(baseStorageClient){
    const indexedDbClient = new baseStorageClient();

    indexedDbClient.storeMedia = function(blob){
         return openDatabase().then(function () {
             const request = database.transaction(storeName, "readwrite")
                .objectStore(storeName)
                .add(dbEntry);

             request.onsuccess = function (event) {
                 logger.log("combined segments saved into database.");
                 // todo - figure out how to resolve here
                 return {
                    IMPORTANTKEY: dbEntry.mediaId //          <---- This too
                 }
              };

              request.onerror = function (event) {
                  // todo: figure out how to reject here
                  logger.log("Unable to save segments " + e);
              };
         });
    }
})

这个客户端在我的storageInterface中使用:

define(["indexedDbClient"], function(indexedDbClient){
    const storageInterface = {};
    var currentClient = indexedDbClient; // might be other clients
    storageInterface.storeMedia = function (blob) {
        return currentClient.storeMedia(blob).then(function(mediaPath) {
            return currentClient.storeMetadata(eventType, mediaPath);
        });
    }
});

这就是事情变得非常棘手的地方。我想要实现的目标如下:

 storageInterface.storeMedia(superBuffer).then(function (importantStuff) {
       // this should go storeMedia > baseStorageClient > eventService
       importantStuff.IMPORTANTKEY;
       importantStuff.IMPORTANTDATA;         
 });

但我不太清楚如何处理这个问题。我怎样才能沿着这样的 promise 链编译结果?

最佳答案

有两个主要问题:

  • 您应该将 donefail 视为已弃用。它们不允许任何链接,它们将丢弃回调的结果。 始终使用then

    sendRequest = function(data){
        return $.ajax(data).then(function(response){
            return response.IMPORTANTDATA;
        }, function(response) {
           throw new Error(response);
        });
    }
    
  • 您的交易尚未返回任何 promise ,因此您没有任何东西可以链接。您需要promisify首先:

    function promiseFromRequest(req) {
        return new Promise(function(resolve, reject) {
            req.onsuccess = resolve;
            req.onerror = reject;
        });
    }
    

    现在你可以像这样实际使用它:

    storeMedia = function(blob){
        return openDatabase().then(function () {
            return promiseFromRequest(database.transaction(storeName, "readwrite")
            .objectStore(storeName)
            .add(dbEntry))
            .then(function (event) {
                logger.log("combined segments saved into database.");
                return {
                    IMPORTANTKEY: dbEntry.mediaId
                }
            }, function (e) {
                logger.log("Unable to save segments " + e);
                throw e;
            };
        });
    };
    

有了这些,您应该能够combine以某种方式从 storeMediastoreMetaData 获取结果。

关于javascript - 通过一系列 promise (JS 继承/接口(interface))编译结果,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44296155/

相关文章:

javascript - 在 Extjs 4.2.0 中将附加参数传递给回调函数

jquery - 是否有适用于触摸移动设备的 HTML5/jQuery 球形全景查看器

javascript - 使用 Ajax 将数组传递给 PHP 脚本会导致空帖子

php - Laravel 5 应用程序 - AJAX Post 请求不接受 token 并抛出 500 内部服务器错误

javascript - 如何从 css 中的 UI 中完全删除底部滚动条

javascript - 带有自定义过滤器菜单的 Kendo Grid 不起作用

javascript - 使用 Google Pay JavaScript API 时防止客户端篡改

javascript - 绑定(bind) .click 和 .blur 事件处理程序

javascript - 如何通过Jquery滑动Slider的元素

javascript - jQuery $.ajax成功一定是回调函数?