diff --git a/lib/hk-util.js b/lib/hk-util.js index 14263e481..4fa2140f9 100644 --- a/lib/hk-util.js +++ b/lib/hk-util.js @@ -419,9 +419,11 @@ const getHistoryOffset = (Env, channelName, lastKnownHash, _cb) => { // fall through to the next block if the offset of the hash in question is not in memory if (lastKnownHash && typeof(lkh) !== "number") { return; } + // If we have a lastKnownHash or we didn't ask for one, we don't need the next blocks + waitFor.abort(); + // Since last 2 checkpoints if (!lastKnownHash) { - waitFor.abort(); // Less than 2 checkpoints in the history: return everything if (index.cpIndex.length < 2) { return void cb(null, 0); } // Otherwise return the second last checkpoint's index @@ -436,7 +438,14 @@ const getHistoryOffset = (Env, channelName, lastKnownHash, _cb) => { to reconcile their differences. */ } - offset = lkh; + // If our lastKnownHash is older than the 2nd to last checkpoint, + // only send the last 2 checkpoints and ignore "lkh" + if (lkh && index.cpIndex.length >= 2 && lkh < index.cpIndex[0].offset) { + return void cb(null, index.cpIndex[0].offset); + } + + // Otherwise use our lastKnownHash + cb(null, lkh); })); }).nThen((w) => { // skip past this block if the offset is anything other than -1 diff --git a/www/common/outer/async-store.js b/www/common/outer/async-store.js index 62e078050..a39734dc4 100644 --- a/www/common/outer/async-store.js +++ b/www/common/outer/async-store.js @@ -10,6 +10,7 @@ define([ '/common/common-realtime.js', '/common/common-messaging.js', '/common/pinpad.js', + '/common/outer/cache-store.js', '/common/outer/sharedfolder.js', '/common/outer/cursor.js', '/common/outer/onlyoffice.js', @@ -28,7 +29,7 @@ define([ '/bower_components/nthen/index.js', '/bower_components/saferphore/index.js', ], function (Sortify, UserObject, ProxyManager, Migrate, Hash, Util, Constants, Feedback, - Realtime, Messaging, Pinpad, + Realtime, Messaging, Pinpad, Cache, SF, Cursor, OnlyOffice, Mailbox, Profile, Team, Messenger, History, NetConfig, AppConfig, Crypto, ChainPad, CpNetflux, Listmap, nThen, Saferphore) { @@ -1590,6 +1591,7 @@ define([ Store.leavePad(null, data, function () {}); }; var conf = { + Cache: Cache, onReady: function (pad) { var padData = pad.metadata || {}; channel.data = padData; @@ -2640,6 +2642,7 @@ define([ readOnly: false, validateKey: secret.keys.validateKey || undefined, crypto: Crypto.createEncryptor(secret.keys), + Cache: Cache, userName: 'fs', logLevel: 1, ChainPad: ChainPad, diff --git a/www/common/outer/cache-store.js b/www/common/outer/cache-store.js new file mode 100644 index 000000000..139501872 --- /dev/null +++ b/www/common/outer/cache-store.js @@ -0,0 +1,55 @@ +define([ + '/bower_components/localforage/dist/localforage.min.js', +], function (localForage) { + var S = {}; + + var cache = localForage.createInstance({ + name: "cp_cache" + }); + + // id: channel ID or blob ID + // returns array of messages + S.getChannelCache = function (id, cb) { + cache.getItem(id, function (err, obj) { + if (err || !obj || !Array.isArray(obj.c)) { + return void cb(err || 'EINVAL'); + } + cb(null, obj); + }); + }; + + var checkCheckpoints = function (array) { + if (!Array.isArray(array)) { return; } + var cp = 0; + for (var i = array.length - 1; i >= 0; i--) { + if (array[i].isCheckpoint) { cp++; } + if (cp === 2) { + array.splice(0, i); + break; + } + } + }; + + S.storeCache = function (id, validateKey, val, cb) { + cb = cb || function () {}; + if (!Array.isArray(val) || !validateKey) { return void cb('EINVAL'); } + checkCheckpoints(val); + cache.setItem(id, { + k: validateKey, + c: val + }, function (err) { + cb(err); + }); + }; + + S.clearChannel = function (id, cb) { + cb = cb || function () {}; + cache.removeItem(id, cb); + }; + + S.clear = function () { + cache.clear(); + }; + + return S; +}); diff --git a/www/common/outer/sharedfolder.js b/www/common/outer/sharedfolder.js index e34cd64df..3c1c8632d 100644 --- a/www/common/outer/sharedfolder.js +++ b/www/common/outer/sharedfolder.js @@ -2,12 +2,13 @@ define([ '/common/common-hash.js', '/common/common-util.js', '/common/userObject.js', + '/common/outer/cache-store.js', '/bower_components/nthen/index.js', '/bower_components/chainpad-crypto/crypto.js', '/bower_components/chainpad-listmap/chainpad-listmap.js', '/bower_components/chainpad/chainpad.dist.js', -], function (Hash, Util, UserObject, +], function (Hash, Util, UserObject, Cache, nThen, Crypto, Listmap, ChainPad) { var SF = {}; @@ -174,6 +175,7 @@ define([ ChainPad: ChainPad, classic: true, network: network, + Cache: Cache, metadata: { validateKey: secret.keys.validateKey || undefined, owners: owners diff --git a/www/common/outer/team.js b/www/common/outer/team.js index de9206511..dc078a2f4 100644 --- a/www/common/outer/team.js +++ b/www/common/outer/team.js @@ -12,6 +12,7 @@ define([ '/common/common-feedback.js', '/common/outer/invitation.js', '/common/cryptget.js', + '/common/outer/cache-store.js', '/bower_components/chainpad-listmap/chainpad-listmap.js', '/bower_components/chainpad-crypto/crypto.js', @@ -21,7 +22,7 @@ define([ '/bower_components/saferphore/index.js', '/bower_components/tweetnacl/nacl-fast.min.js', ], function (Util, Hash, Constants, Realtime, - ProxyManager, UserObject, SF, Roster, Messaging, Feedback, Invite, Crypt, + ProxyManager, UserObject, SF, Roster, Messaging, Feedback, Invite, Crypt, Cache, Listmap, Crypto, CpNetflux, ChainPad, nThen, Saferphore) { var Team = {}; @@ -426,6 +427,7 @@ define([ channel: secret.channel, crypto: crypto, ChainPad: ChainPad, + Cache: Cache, metadata: { validateKey: secret.keys.validateKey || undefined, }, @@ -573,6 +575,7 @@ define([ logLevel: 1, classic: true, ChainPad: ChainPad, + Cache: Cache, owners: [ctx.store.proxy.edPublic] }; nThen(function (waitFor) {