我正在构建一个“存储提供程序”,允许使用代码通过接口(interface)存储内容。将下面的代码片段视为伪代码,因为我要使用 MCVE。我正在尝试获取下面的 IMPORTANTDATA
和 IMPORTANTKEY
。
在最低级别,我有一个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 链编译结果?
最佳答案
有两个主要问题:
您应该将
done
和fail
视为已弃用。它们不允许任何链接,它们将丢弃回调的结果。 始终使用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以某种方式从 storeMedia
和 storeMetaData
获取结果。
关于javascript - 通过一系列 promise (JS 继承/接口(interface))编译结果,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44296155/