diff --git a/dev/App/User.jsx b/dev/App/User.jsx index 8b83669ca..6d466f514 100644 --- a/dev/App/User.jsx +++ b/dev/App/User.jsx @@ -409,7 +409,7 @@ class AppUser extends AbstractApp { callback(!!value); } - }).fail(() => { + }).catch(() => { if (callback) { _.delay(() => callback(false), 1); @@ -423,7 +423,7 @@ class AppUser extends AbstractApp .abort('Folders') .fastResolve(true) .then(() => promise) - .fail((errorCode) => { + .catch((errorCode) => { FolderStore.folderList.error(Translator.getNotification(errorCode, '', errorDefCode)); }).fin(() => { Promises.foldersReloadWithTimeout(FolderStore.foldersLoading); @@ -453,14 +453,18 @@ class AppUser extends AbstractApp : (oItem.users && oItem.users[0] ? oItem.users[0].userId.userid : '') ; - if (oItem.users) { + if (oItem.users) + { _.each(oItem.users, (item) => { - oEmail.clear(); - oEmail.mailsoParse(item.userId.userid); - if (oEmail.validate()) + if (item.userId) { - aEmails.push(oEmail.email); - aUsers.push(item.userId.userid); + oEmail.clear(); + oEmail.mailsoParse(item.userId.userid); + if (oEmail.validate()) + { + aEmails.push(oEmail.email); + aUsers.push(item.userId.userid); + } } }); } diff --git a/dev/Promises/AbstractAjax.js b/dev/Promises/AbstractAjax.js index 9e2fd22d6..efc6b28ee 100644 --- a/dev/Promises/AbstractAjax.js +++ b/dev/Promises/AbstractAjax.js @@ -6,7 +6,7 @@ var $ = require('$'), _ = require('_'), - Q = require('Q'), + Promise = require('Promise'), Consts = require('Common/Consts'), Enums = require('Common/Enums'), @@ -58,151 +58,151 @@ AbstractAjaxPromises.prototype.ajaxRequest = function (sAction, bPost, iTimeOut, oParameters, sAdditionalGetString, fTrigger) { - var - oH = null, - self = this, - iStart = Utils.microtime(), - oDeferred = Q.defer() - ; + var self = this; + return new Promise(function(resolve, reject) { - iTimeOut = Utils.isNormal(iTimeOut) ? iTimeOut : Consts.DEFAULT_AJAX_TIMEOUT; - sAdditionalGetString = Utils.isUnd(sAdditionalGetString) ? '' : Utils.pString(sAdditionalGetString); + var + oH = null, + iStart = Utils.microtime() + ; - if (bPost) - { - oParameters['XToken'] = Settings.appSettingsGet('token'); - } + iTimeOut = Utils.isNormal(iTimeOut) ? iTimeOut : Consts.DEFAULT_AJAX_TIMEOUT; + sAdditionalGetString = Utils.isUnd(sAdditionalGetString) ? '' : Utils.pString(sAdditionalGetString); - Plugins.runHook('ajax-default-request', [sAction, oParameters, sAdditionalGetString]); - - this.setTrigger(fTrigger, true); - - oH = $.ajax({ - 'type': bPost ? 'POST' : 'GET', - 'url': Links.ajax(sAdditionalGetString), - 'async': true, - 'dataType': 'json', - 'data': bPost ? (oParameters || {}) : {}, - 'timeout': iTimeOut, - 'global': true - }).always(function (oData, sTextStatus) { - - var bCached = false, oErrorData = null, sType = Enums.StorageResultType.Error; - if (oData && oData['Time']) + if (bPost) { - bCached = Utils.pInt(oData['Time']) > Utils.microtime() - iStart; + oParameters['XToken'] = Settings.appSettingsGet('token'); } - // backward capability - switch (true) - { - case 'success' === sTextStatus && oData && oData.Result && sAction === oData.Action: - sType = Enums.StorageResultType.Success; - break; - case 'abort' === sTextStatus && (!oData || !oData.__aborted__): - sType = Enums.StorageResultType.Abort; - break; - } + Plugins.runHook('ajax-default-request', [sAction, oParameters, sAdditionalGetString]); - Plugins.runHook('ajax-default-response', [sAction, - Enums.StorageResultType.Success === sType ? oData : null, sType, bCached, oParameters]); + self.setTrigger(fTrigger, true); - if ('success' === sTextStatus) - { - if (oData && oData.Result && sAction === oData.Action) + oH = $.ajax({ + 'type': bPost ? 'POST' : 'GET', + 'url': Links.ajax(sAdditionalGetString), + 'async': true, + 'dataType': 'json', + 'data': bPost ? (oParameters || {}) : {}, + 'timeout': iTimeOut, + 'global': true + }).always(function (oData, sTextStatus) { + + var bCached = false, oErrorData = null, sType = Enums.StorageResultType.Error; + if (oData && oData['Time']) { - oData.__cached__ = bCached; - oDeferred.resolve(oData); + bCached = Utils.pInt(oData['Time']) > Utils.microtime() - iStart; } - else if (oData && oData.Action) + + // backward capability + switch (true) + { + case 'success' === sTextStatus && oData && oData.Result && sAction === oData.Action: + sType = Enums.StorageResultType.Success; + break; + case 'abort' === sTextStatus && (!oData || !oData.__aborted__): + sType = Enums.StorageResultType.Abort; + break; + } + + Plugins.runHook('ajax-default-response', [sAction, + Enums.StorageResultType.Success === sType ? oData : null, sType, bCached, oParameters]); + + if ('success' === sTextStatus) + { + if (oData && oData.Result && sAction === oData.Action) + { + oData.__cached__ = bCached; + resolve(oData); + } + else if (oData && oData.Action) + { + oErrorData = oData; + reject(oData.ErrorCode ? oData.ErrorCode : Enums.Notification.AjaxFalse); + } + else + { + oErrorData = oData; + reject(Enums.Notification.AjaxParse); + } + } + else if ('timeout' === sTextStatus) { oErrorData = oData; - oDeferred.reject(oData.ErrorCode ? oData.ErrorCode : Enums.Notification.AjaxFalse); + reject(Enums.Notification.AjaxTimeout); + } + else if ('abort' === sTextStatus) + { + if (!oData || !oData.__aborted__) + { + reject(Enums.Notification.AjaxAbort); + } } else { oErrorData = oData; - oDeferred.reject(Enums.Notification.AjaxParse); - } - } - else if ('timeout' === sTextStatus) - { - oErrorData = oData; - oDeferred.reject(Enums.Notification.AjaxTimeout); - } - else if ('abort' === sTextStatus) - { - if (!oData || !oData.__aborted__) - { - oDeferred.reject(Enums.Notification.AjaxAbort); - } - } - else - { - oErrorData = oData; - oDeferred.reject(Enums.Notification.AjaxParse); - } - - if (self.oRequests[sAction]) - { - self.oRequests[sAction] = null; - delete self.oRequests[sAction]; - } - - self.setTrigger(fTrigger, false); - - if (oErrorData) - { - if (-1 < Utils.inArray(oErrorData.ErrorCode, [ - Enums.Notification.AuthError, Enums.Notification.AccessError, - Enums.Notification.ConnectionError, Enums.Notification.DomainNotAllowed, Enums.Notification.AccountNotAllowed, - Enums.Notification.MailServerError, Enums.Notification.UnknownNotification, Enums.Notification.UnknownError - ])) - { - Globals.iAjaxErrorCount++; + reject(Enums.Notification.AjaxParse); } - if (Enums.Notification.InvalidToken === oErrorData.ErrorCode) + if (self.oRequests[sAction]) { - Globals.iTokenErrorCount++; + self.oRequests[sAction] = null; + delete self.oRequests[sAction]; } - if (Consts.TOKEN_ERROR_LIMIT < Globals.iTokenErrorCount) + self.setTrigger(fTrigger, false); + + if (oErrorData) { - if (Globals.__APP__ && Globals.__APP__.loginAndLogoutReload) + if (-1 < Utils.inArray(oErrorData.ErrorCode, [ + Enums.Notification.AuthError, Enums.Notification.AccessError, + Enums.Notification.ConnectionError, Enums.Notification.DomainNotAllowed, Enums.Notification.AccountNotAllowed, + Enums.Notification.MailServerError, Enums.Notification.UnknownNotification, Enums.Notification.UnknownError + ])) { - Globals.__APP__.loginAndLogoutReload(false, true); + Globals.iAjaxErrorCount++; + } + + if (Enums.Notification.InvalidToken === oErrorData.ErrorCode) + { + Globals.iTokenErrorCount++; + } + + if (Consts.TOKEN_ERROR_LIMIT < Globals.iTokenErrorCount) + { + if (Globals.__APP__ && Globals.__APP__.loginAndLogoutReload) + { + Globals.__APP__.loginAndLogoutReload(false, true); + } + } + + if (oErrorData.ClearAuth || oErrorData.Logout || Consts.AJAX_ERROR_LIMIT < Globals.iAjaxErrorCount) + { + if (Globals.__APP__ && Globals.__APP__.clearClientSideToken) + { + Globals.__APP__.clearClientSideToken(); + } + + if (Globals.__APP__ && !oErrorData.ClearAuth && Globals.__APP__.loginAndLogoutReload) + { + Globals.__APP__.loginAndLogoutReload(false, true); + } } } - if (oErrorData.ClearAuth || oErrorData.Logout || Consts.AJAX_ERROR_LIMIT < Globals.iAjaxErrorCount) + }); + + if (oH) + { + if (self.oRequests[sAction]) { - if (Globals.__APP__ && Globals.__APP__.clearClientSideToken) - { - Globals.__APP__.clearClientSideToken(); - } - - if (Globals.__APP__ && !oErrorData.ClearAuth && Globals.__APP__.loginAndLogoutReload) - { - Globals.__APP__.loginAndLogoutReload(false, true); - } + self.oRequests[sAction] = null; + delete self.oRequests[sAction]; } - } + self.oRequests[sAction] = oH; + } }); - - if (oH) - { - if (this.oRequests[sAction]) - { - this.oRequests[sAction] = null; - delete this.oRequests[sAction]; - } - - this.oRequests[sAction] = oH; - } - - return oDeferred.promise; }; AbstractAjaxPromises.prototype.getRequest = function (sAction, fTrigger, sAdditionalGetString, iTimeOut) diff --git a/dev/Promises/AbstractBasic.js b/dev/Promises/AbstractBasic.js index 79996e615..b8cc2a1da 100644 --- a/dev/Promises/AbstractBasic.js +++ b/dev/Promises/AbstractBasic.js @@ -5,7 +5,7 @@ var _ = require('_'), - Q = require('Q'), + Promise = require('Promise'), Utils = require('Common/Utils') ; @@ -26,16 +26,12 @@ AbstractBasicPromises.prototype.fastResolve = function (mData) { - var oDeferred = Q.defer(); - oDeferred.resolve(mData); - return oDeferred.promise; + return Promise.resolve(mData); }; AbstractBasicPromises.prototype.fastReject = function (mData) { - var oDeferred = Q.defer(); - oDeferred.reject(mData); - return oDeferred.promise; + return Promise.reject(mData); }; AbstractBasicPromises.prototype.setTrigger = function (mTrigger, bValue) diff --git a/dev/Stores/User/Pgp.js b/dev/Stores/User/Pgp.js index 12f9253e1..c0d52dbff 100644 --- a/dev/Stores/User/Pgp.js +++ b/dev/Stores/User/Pgp.js @@ -9,6 +9,7 @@ kn = require('Knoin/Knoin'), Translator = require('Common/Translator'), + Settings = require('Storage/Settings'), Utils = require('Common/Utils') ; @@ -237,6 +238,23 @@ return false; }; + PgpUserStore.prototype.findKeyExternal = function (sEmail, fCallback) + { + if (this.openpgp.HKP && Settings.appSettingsGet('openpgpPublicKeyServer')) + { + var oHkp = new this.openpgp.HKP(Settings.appSettingsGet('openpgpPublicKeyServer').replace(/\/$/, '')); + oHkp.lookup({query: sEmail}).then(function(sKey) { + fCallback(sKey); + }, function() { + fCallback(null); + }); + } + else + { + fCallback(null); + } + }; + PgpUserStore.prototype.verifyMessage = function (oMessage, fCallback) { var oValid = null, aResult = [], aPublicKeys = [], aSigningKeyIds = []; @@ -245,6 +263,10 @@ aSigningKeyIds = oMessage.getSigningKeyIds(); if (aSigningKeyIds && 0 < aSigningKeyIds.length) { +// this.findKeyExternal('support@rainloop.net', function(key) { +// console.log(key); +// }); + aPublicKeys = this.findPublicKeysBySigningKeyIds(aSigningKeyIds); if (aPublicKeys && 0 < aPublicKeys.length) { diff --git a/dev/View/User/MailBox/MessageView.js b/dev/View/User/MailBox/MessageView.js index b7741206f..415eebb33 100644 --- a/dev/View/User/MailBox/MessageView.js +++ b/dev/View/User/MailBox/MessageView.js @@ -1078,7 +1078,7 @@ { self.downloadAsZipError(true); } - }).fail(function () { + }).catch(function () { self.downloadAsZipError(true); }); } @@ -1102,7 +1102,7 @@ { self.saveToOwnCloudError(true); } - }).fail(function () { + }).catch(function () { self.saveToOwnCloudError(true); }); } @@ -1159,7 +1159,7 @@ self.saveToDropboxError(true); } } - }).fail(function () { + }).catch(function () { self.saveToDropboxError(true); }); } diff --git a/gulpfile.js b/gulpfile.js index 03e562df3..6afaf839f 100644 --- a/gulpfile.js +++ b/gulpfile.js @@ -193,7 +193,6 @@ cfg.paths.js = { 'vendors/knockout-sortable/knockout-sortable.min.js', 'vendors/ssm/ssm.min.js', 'vendors/jua/jua.min.js', - 'vendors/Q/q.min.js', 'vendors/opentip/opentip-jquery.min.js', 'vendors/Autolinker/Autolinker.min.js', 'vendors/lightGallery/dist/js/lightgallery.min.js', diff --git a/package.json b/package.json index 99e29cc59..91446448a 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "RainLoop", "title": "RainLoop Webmail", "version": "1.10.1", - "release": "117", + "release": "118", "ownCloudPackageVersion": "4.17", "description": "Simple, modern & fast web-based email client", "homepage": "http://rainloop.net", diff --git a/rainloop/v/0.0.0/app/libraries/RainLoop/Actions.php b/rainloop/v/0.0.0/app/libraries/RainLoop/Actions.php index c7fe78958..f6b516759 100644 --- a/rainloop/v/0.0.0/app/libraries/RainLoop/Actions.php +++ b/rainloop/v/0.0.0/app/libraries/RainLoop/Actions.php @@ -1478,7 +1478,8 @@ class Actions 'languages' => $this->GetLanguages(false), 'languagesAdmin' => $this->GetLanguages(true), 'attachmentsActions' => $aAttachmentsActions, - 'rsaPublicKey' => $sRsaPublicKey + 'rsaPublicKey' => $sRsaPublicKey, + 'openpgpPublicKeyServer' => $oConfig->Get('security', 'openpgp_public_key_server', '') ), $bAdmin ? array( 'adminPath' => \strtolower($oConfig->Get('security', 'admin_panel_key', 'admin')), 'allowAdminPanel' => (bool) $oConfig->Get('security', 'allow_admin_panel', true), diff --git a/rainloop/v/0.0.0/app/libraries/RainLoop/Config/Application.php b/rainloop/v/0.0.0/app/libraries/RainLoop/Config/Application.php index 6ead58df5..efc9ceeae 100644 --- a/rainloop/v/0.0.0/app/libraries/RainLoop/Config/Application.php +++ b/rainloop/v/0.0.0/app/libraries/RainLoop/Config/Application.php @@ -197,7 +197,10 @@ class Application extends \RainLoop\Config\AbstractConfig 'custom_server_signature' => array('RainLoop'), 'x_frame_options_header' => array(''), + 'openpgp' => array(false), + 'openpgp_public_key_server' => array(''), + 'use_rsa_encryption' => array(false), 'admin_login' => array('admin', 'Login and password for web admin panel'), 'admin_password' => array('12345'), @@ -357,7 +360,7 @@ Enables caching in the system'), 'index' => array('v1', 'Additional caching key. If changed, cache is purged'), - 'fast_cache_driver' => array('files', 'Can be: files, APC, memcache, redis'), + 'fast_cache_driver' => array('files', 'Can be: files, APC, memcache, redis (beta)'), 'fast_cache_index' => array('v1', 'Additional caching key. If changed, fast cache is purged'), 'http' => array(true, 'Browser-level cache. If enabled, caching is maintainted without using files'), diff --git a/webpack.config.js b/webpack.config.js index a9c721ce6..363a815fd 100644 --- a/webpack.config.js +++ b/webpack.config.js @@ -73,7 +73,7 @@ module.exports = { 'ssm': 'window.ssm', 'key': 'window.key', '_': 'window._', - 'Q': 'window.Q', + 'Promise': 'window.Promise', '$': 'window.jQuery' } }; \ No newline at end of file