Bug 1435000 - Refactor client engine queue to use AsyncQueueCaller r?eoger draft
authorCarol Ng <cng@mozilla.com>
Tue, 29 May 2018 14:30:22 -0400
changeset 801126 245950775d24
parent 798691 d36cd8bdbc5c
push id111583
push userbmo:cng@mozilla.com
push dateTue, 29 May 2018 19:43:07 +0000
reviewerseoger
bugs1435000
milestone62.0a1
Bug 1435000 - Refactor client engine queue to use AsyncQueueCaller r?eoger MozReview-Commit-ID: JRWHktfqGMQ
services/common/async.js
services/sync/modules/engines/clients.js
--- a/services/common/async.js
+++ b/services/common/async.js
@@ -158,19 +158,20 @@ class AsyncQueueCaller {
   /**
    * /!\ Never await on another function that calls enqueueCall /!\
    *     on the same queue or we will deadlock.
    */
   enqueueCall(func) {
     this._queue = (async () => {
       await this._queue;
       try {
-        await func();
+        return await func();
       } catch (e) {
         this._log.error(e);
+        return false;
       }
     })();
   }
 
   promiseCallsComplete() {
     return this._queue;
   }
 }
--- a/services/sync/modules/engines/clients.js
+++ b/services/sync/modules/engines/clients.js
@@ -81,17 +81,17 @@ Utils.deferGetSet(ClientsRec,
                    "formfactor", "os", "appPackage", "application", "device",
                    "fxaDeviceId"]);
 
 
 function ClientEngine(service) {
   SyncEngine.call(this, "Clients", service);
 
   this.fxAccounts = fxAccounts;
-  this.addClientCommandQueue = Promise.resolve();
+  this.addClientCommandQueue = Async.asyncQueueCaller(this._log);
   Utils.defineLazyIDProperty(this, "localID", "services.sync.client.GUID");
 }
 ClientEngine.prototype = {
   __proto__: SyncEngine.prototype,
   _storeObj: ClientStore,
   _recordObj: ClientsRec,
   _trackerObj: ClientsTracker,
   allowSkippedRecord: false,
@@ -288,18 +288,17 @@ ClientEngine.prototype = {
 
   async removeLocalCommand(command) {
     // the implementation of this engine is such that adding a command to
     // the local client is how commands are deleted! ¯\_(ツ)_/¯
     await this._addClientCommand(this.localID, command);
   },
 
   async _addClientCommand(clientId, command) {
-    return this.addClientCommandQueue = (async () => {
-      await this.addClientCommandQueue;
+    this.addClientCommandQueue.enqueueCall(async () => {
       try {
         const localCommands = await this._readCommands();
         const localClientCommands = localCommands[clientId] || [];
         const remoteClient = this._store._remoteClients[clientId];
         let remoteClientCommands = [];
         if (remoteClient && remoteClient.commands) {
           remoteClientCommands = remoteClient.commands;
         }
@@ -310,17 +309,19 @@ ClientEngine.prototype = {
         localCommands[clientId] = localClientCommands.concat(command);
         await this._saveCommands(localCommands);
         return true;
       } catch (e) {
         // Failing to save a command should not "break the queue" of pending operations.
         this._log.error(e);
         return false;
       }
-    })();
+    });
+
+    return this.addClientCommandQueue.promiseCallsComplete();
   },
 
   async _removeClientCommands(clientId) {
     const allCommands = await this._readCommands();
     delete allCommands[clientId];
     await this._saveCommands(allCommands);
   },