From a5923c2177593ebf963fa32d0c5fcbc7692c47b7 Mon Sep 17 00:00:00 2001 From: Scott Nonnenberg Date: Thu, 30 Nov 2017 11:55:59 -0800 Subject: [PATCH] Key rotation: log failures, retry, force on new version (#1833) * Retry failed signed key rotation; start rotation when registered (#1772) * rotateSignedPrekeys: Fix 'res is not defined' error * If the server rejects key rotation, don't retry immediately * Force a signed key rotation on launch of any new version --- js/background.js | 4 +++- js/libtextsecure.js | 19 +++++++++++++------ js/rotate_signed_prekey_listener.js | 13 ++++++++++++- libtextsecure/account_manager.js | 19 +++++++++++++------ 4 files changed, 41 insertions(+), 14 deletions(-) diff --git a/js/background.js b/js/background.js index 3bdabdc89..36fb406e6 100644 --- a/js/background.js +++ b/js/background.js @@ -83,6 +83,7 @@ if (!lastVersion || currentVersion !== lastVersion) { console.log('New version detected:', currentVersion); + getAccountManager().rotateSignedPreKey(); } window.dispatchEvent(new Event('storage_ready')); @@ -90,19 +91,20 @@ console.log('listening for registration events'); Whisper.events.on('registration_done', function() { console.log('handling registration event'); + Whisper.RotateSignedPreKeyListener.init(Whisper.events); connect(true); }); var appView = window.owsDesktopApp.appView = new Whisper.AppView({el: $('body')}); Whisper.WallClockListener.init(Whisper.events); - Whisper.RotateSignedPreKeyListener.init(Whisper.events); Whisper.ExpiringMessagesListener.init(Whisper.events); if (Whisper.Import.isIncomplete()) { console.log('Import was interrupted, showing import error screen'); appView.openImporter(); } else if (Whisper.Registration.everDone()) { + Whisper.RotateSignedPreKeyListener.init(Whisper.events); connect(); appView.openInbox({ initialLoadComplete: initialLoadComplete diff --git a/js/libtextsecure.js b/js/libtextsecure.js index b452eac81..14980063a 100644 --- a/js/libtextsecure.js +++ b/js/libtextsecure.js @@ -38008,13 +38008,20 @@ var TextSecureServer = (function() { return store.storeSignedPreKey(res.keyId, res.keyPair).then(function() { return cleanSignedPreKeys(); }); - }).catch(function(e) { - if (e instanceof Error && e.name == 'HTTPError' && e.code >= 400 && e.code <= 599) { - var rejections = 1 + textsecure.storage.get('signedKeyRotationRejected', 0); - textsecure.storage.put('signedKeyRotationRejected', rejections); - console.log('Signed key rotation rejected count:', rejections); - } }); + }).catch(function(e) { + console.log( + 'rotateSignedPrekey error:', + e && e.stack ? e.stack : e + ); + + if (e instanceof Error && e.name == 'HTTPError' && e.code >= 400 && e.code <= 599) { + var rejections = 1 + textsecure.storage.get('signedKeyRotationRejected', 0); + textsecure.storage.put('signedKeyRotationRejected', rejections); + console.log('Signed key rotation rejected count:', rejections); + } else { + throw e; + } }); }.bind(this)); }, diff --git a/js/rotate_signed_prekey_listener.js b/js/rotate_signed_prekey_listener.js index 43fe6ff82..a52ece8e3 100644 --- a/js/rotate_signed_prekey_listener.js +++ b/js/rotate_signed_prekey_listener.js @@ -17,7 +17,10 @@ function run() { console.log('Rotating signed prekey...'); - getAccountManager().rotateSignedPreKey(); + getAccountManager().rotateSignedPreKey().catch(function() { + console.log('rotateSignedPrekey() failed. Trying again in five seconds'); + setTimeout(runWhenOnline, 5000); + }); scheduleNextRotation(); setTimeoutForNextRun(); } @@ -26,6 +29,7 @@ if (navigator.onLine) { run(); } else { + console.log('We are offline; keys will be rotated when we are next online'); var listener = function() { window.removeEventListener('online', listener); run(); @@ -52,8 +56,15 @@ timeout = setTimeout(runWhenOnline, waitTime); } + var initComplete; Whisper.RotateSignedPreKeyListener = { init: function(events) { + if (initComplete) { + console.log('Rotate signed prekey listener: Already initialized'); + return; + } + initComplete = true; + if (Whisper.Registration.isDone()) { setTimeoutForNextRun(); } diff --git a/libtextsecure/account_manager.js b/libtextsecure/account_manager.js index 61c06a44c..45c904059 100644 --- a/libtextsecure/account_manager.js +++ b/libtextsecure/account_manager.js @@ -138,13 +138,20 @@ return store.storeSignedPreKey(res.keyId, res.keyPair).then(function() { return cleanSignedPreKeys(); }); - }).catch(function(e) { - if (e instanceof Error && e.name == 'HTTPError' && e.code >= 400 && e.code <= 599) { - var rejections = 1 + textsecure.storage.get('signedKeyRotationRejected', 0); - textsecure.storage.put('signedKeyRotationRejected', rejections); - console.log('Signed key rotation rejected count:', rejections); - } }); + }).catch(function(e) { + console.log( + 'rotateSignedPrekey error:', + e && e.stack ? e.stack : e + ); + + if (e instanceof Error && e.name == 'HTTPError' && e.code >= 400 && e.code <= 599) { + var rejections = 1 + textsecure.storage.get('signedKeyRotationRejected', 0); + textsecure.storage.put('signedKeyRotationRejected', rejections); + console.log('Signed key rotation rejected count:', rejections); + } else { + throw e; + } }); }.bind(this)); },