From 3a00a9c3c052574deb992fb3138cb7530b5c07d0 Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 13:49:05 -0300 Subject: [PATCH 1/8] Rename Index to StoreIndex --- src/Store.js | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/src/Store.js b/src/Store.js index c205ea2..5b5e1e5 100644 --- a/src/Store.js +++ b/src/Store.js @@ -4,16 +4,17 @@ const EventEmitter = require('events').EventEmitter const Readable = require('readable-stream') const mapSeries = require('p-each-series') const Log = require('ipfs-log') -const Index = require('./Index') +const Logger = require('logplease') + +const StoreIndex = require('./Index') const Replicator = require('./Replicator') const ReplicationInfo = require('./replication-info') -const Logger = require('logplease') const logger = Logger.create("orbit-db.store", { color: Logger.Colors.Blue }) Logger.setLogLevel('ERROR') const DefaultOptions = { - Index: Index, + Index: StoreIndex, maxHistory: -1, path: './orbitdb', replicate: true, @@ -57,8 +58,10 @@ class Store { } this.access = options.accessController || defaultAccess - // Create the operations log - this._oplog = new Log(this._ipfs, this.id, null, null, null, this._key, this.access.write) + // Caching and Index + const { cache, Index } = this.options + this._cache = cache + this._index = new Index(this.uid) // Create the index this._index = new this.options.Index(this.uid) From fccb38d18a2fa096c48a136eabdb8e28cc303c23 Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 13:50:20 -0300 Subject: [PATCH 2/8] Extend EventEmitter --- src/Store.js | 53 +++++++++++++++++++++------------------------------- 1 file changed, 21 insertions(+), 32 deletions(-) diff --git a/src/Store.js b/src/Store.js index 5b5e1e5..5065877 100644 --- a/src/Store.js +++ b/src/Store.js @@ -22,15 +22,9 @@ const DefaultOptions = { replicationConcurrency: 128, } -class Store { - constructor (ipfs, peerId, address, options) { - // Set the options - let opts = Object.assign({}, DefaultOptions) - Object.assign(opts, options) - this.options = opts - - // Default type - this._type = 'store' +class Store extends EventEmitter { + constructor(ipfs, peerId, address, options) { + super() // Create IDs, names and paths this.id = address.toString() @@ -168,22 +162,16 @@ class Store { } // Remove all event listeners - this.events.removeAllListeners('load') - this.events.removeAllListeners('load.progress') - this.events.removeAllListeners('replicate') - this.events.removeAllListeners('replicate.progress') - this.events.removeAllListeners('replicated') - this.events.removeAllListeners('ready') - this.events.removeAllListeners('write') + this.removeAllListeners('load') + this.removeAllListeners('load.progress') + this.removeAllListeners('replicate') + this.removeAllListeners('replicate.progress') + this.removeAllListeners('replicated') + this.removeAllListeners('ready') + this.removeAllListeners('write') // Close cache await this._cache.close() - - // Database is now closed - // TODO: afaik we don't use 'closed' event anymore, - // to be removed in future releases - this.events.emit('closed', this.address.toString()) - return Promise.resolve() } /** @@ -207,7 +195,7 @@ class Store { const heads = localHeads.concat(remoteHeads) if (heads.length > 0) - this.events.emit('load', this.address.toString(), heads) + this.emit('load', this.address.toString(), heads) await mapSeries(heads, async (head) => { this._recalculateReplicationMax(head.clock.time) @@ -219,7 +207,7 @@ class Store { if (heads.length > 0) await this._updateIndex() - this.events.emit('ready', this.address.toString(), this._oplog.heads) + this.emit('ready', this.address.toString(), this._oplog.heads) } sync (heads) { @@ -313,15 +301,13 @@ class Store { } async loadFromSnapshot (onProgressCallback) { - this.events.emit('load', this.address.toString()) + this.emit('load', this.address.toString()) const maxClock = (res, val) => Math.max(res, val.clock.time) - const queue = await this._cache.get('queue') this.sync(queue || []) const snapshot = await this._cache.get('snapshot') - if (snapshot) { const res = await this._ipfs.files.catReadableStream(snapshot.hash) const loadSnapshotData = () => { @@ -403,9 +389,9 @@ class Store { const log = await Log.fromJSON(this._ipfs, snapshotData, -1, this._key, this.access.write, 1000, onProgress) await this._oplog.join(log) await this._updateIndex() - this.events.emit('replicated', this.address.toString()) + this.emit('replicated', this.address.toString()) } - this.events.emit('ready', this.address.toString(), this._oplog.heads) + this.emit('ready', this.address.toString(), this._oplog.heads) } else { throw new Error(`Snapshot for ${this.address} not found!`) } @@ -422,11 +408,14 @@ class Store { async _addOperation (data, batchOperation, lastOperation, onProgressCallback) { if (this._oplog) { const entry = await this._oplog.append(data, this.options.referenceCount) - this._recalculateReplicationStatus(this.replicationStatus.progress + 1, entry.clock.time) + this._recalculateReplicationStatus(this._replicationStatus.progress + 1, entry.clock.time) + await this._cache.set('_localHeads', [entry]) await this._updateIndex() - this.events.emit('write', this.address.toString(), entry, this._oplog.heads) + + this.emit('write', this.address.toString(), entry, this._oplog.heads) if (onProgressCallback) onProgressCallback(entry) + return entry.hash } } @@ -437,7 +426,7 @@ class Store { _onLoadProgress (hash, entry, progress, total) { this._recalculateReplicationStatus(progress, total) - this.events.emit('load.progress', this.address.toString(), hash, entry, this.replicationStatus.progress, this.replicationStatus.max) + this.emit('load.progress', this.address.toString(), hash, entry, this._replicationStatus.progress, this._replicationStatus.max) } /* Replication Status state updates */ From 6f164e0788141def7627157a01c367b2bc3e9702 Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 13:51:14 -0300 Subject: [PATCH 3/8] Throw errors for required arguments missing --- src/Store.js | 30 ++++++++++++++++-------------- 1 file changed, 16 insertions(+), 14 deletions(-) diff --git a/src/Store.js b/src/Store.js index 5065877..bf827e0 100644 --- a/src/Store.js +++ b/src/Store.js @@ -26,31 +26,33 @@ class Store extends EventEmitter { constructor(ipfs, peerId, address, options) { super() - // Create IDs, names and paths - this.id = address.toString() - this.uid = peerId - this.address = address - this.dbname = address.path || '' - this.events = new EventEmitter() + if (!ipfs) throw new Error('IPFS instance not defined') + if (!peerId) throw new Error('Peer id is required') + if (!address) throw new Error('Address is required') - // External dependencies this._ipfs = ipfs - this._cache = options.cache + // Default store type + this._type = 'store' + this.address = address + this.dbname = address.path + this.uid = peerId + + this.options = Object.assign({}, DefaultOptions, options) - this._keystore = options.keystore - this._key = options && options.key - ? options.key - : this._keystore.getKey(peerId) || this._keystore.createKey(peerId) + // Access controller + const { accessController, key, keystore } = this.options + if (!accessController) throw new Error('Access controller not defined') + this._keystore = keystore + this._key = key || this._keystore.getKey(peerId) || this._keystore.createKey(peerId) // FIX: duck typed interface this._ipfs.keystore = this._keystore - // Access mapping const defaultAccess = { admin: [this._key.getPublic('hex')], read: [], // Not used atm, anyone can read write: [this._key.getPublic('hex')], } - this.access = options.accessController || defaultAccess + this.access = accessController || defaultAccess // Caching and Index const { cache, Index } = this.options From 5e7cd65e619493e0e152013ee25f653b52472a42 Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 14:04:22 -0300 Subject: [PATCH 4/8] Reorganize replication and progress report info, remove .id property --- src/Store.js | 95 +++++++++++++++++++++++++--------------------------- 1 file changed, 45 insertions(+), 50 deletions(-) diff --git a/src/Store.js b/src/Store.js index bf827e0..c68c387 100644 --- a/src/Store.js +++ b/src/Store.js @@ -59,11 +59,8 @@ class Store extends EventEmitter { this._cache = cache this._index = new Index(this.uid) - // Create the index - this._index = new this.options.Index(this.uid) - - // Replication progress info - this._replicationStatus = new ReplicationInfo() + // Create the operations log + this._oplog = new Log(this._ipfs, this.address.toString(), null, null, null, this._key, this.access.write) // Statistics this._stats = { @@ -73,51 +70,49 @@ class Store extends EventEmitter { syncRequestsReceieved: 0, } - try { - this._replicator = new Replicator(this, this.options.replicationConcurrency) - // For internal backwards compatibility, - // to be removed in future releases - this._loader = this._replicator - this._replicator.on('load.added', (entry) => { - // Update the latest entry state (latest is the entry with largest clock time) - this._replicationStatus.queued ++ - this._recalculateReplicationMax(entry.clock ? entry.clock.time : 0) - // logger.debug(``) - this.events.emit('replicate', this.address.toString(), entry) - }) - this._replicator.on('load.progress', (id, hash, entry, have, bufferedLength) => { - if (this._replicationStatus.buffered > bufferedLength) { - this._recalculateReplicationProgress(this.replicationStatus.progress + bufferedLength) - } else { - this._recalculateReplicationProgress(this._oplog.length + bufferedLength) - } - this._replicationStatus.buffered = bufferedLength - this._recalculateReplicationMax(this.replicationStatus.progress) - // logger.debug(``) - this.events.emit('replicate.progress', this.address.toString(), hash, entry, this.replicationStatus.progress, this.replicationStatus.max) - }) + // Replication progress info + const { referenceCount, replicationConcurrency, replicate } = this.options + this._replicationStatus = new ReplicationInfo() + this._replicator = new Replicator(this, this.options.replicationConcurrency) + this._replicator.on('load.added', this._onLoadAdded.bind(this)) + this._replicator.on('load.progress', this._onReplicatorLoadProgress.bind(this)) + this._replicator.on('load.end', this._onLoadCompleted.bind(this)) + } - const onLoadCompleted = async (logs, have) => { - try { - for (let log of logs) { - await this._oplog.join(log) - } - this._replicationStatus.queued -= logs.length - this._replicationStatus.buffered = this._replicator._buffer.length - await this._updateIndex() - - //only store heads that has been verified and merges - const heads = this._oplog.heads - await this._cache.set('_remoteHeads', heads) - logger.debug(`Saved heads ${heads.length} [${heads.map(e => e.hash).join(', ')}]`) - - // logger.debug(``) - this.events.emit('replicated', this.address.toString(), logs.length) - } catch (e) { - console.error(e) - } + _onReplicatorLoadProgress(id, hash, entry, have, bufferedLength) { + const progress = this._replicationStatus.buffered > bufferedLength ? this._replicationStatus.progress + bufferedLength : this._oplog.length + bufferedLength + this._recalculateReplicationProgress(progress) + this._replicationStatus.buffered = bufferedLength + this._recalculateReplicationMax(this._replicationStatus.progress) + // logger.debug(``) + this.emit('replicate.progress', this.address.toString(), hash, entry, this._replicationStatus.progress, this._replicationStatus.max) + } + + _onLoadAdded (entry) { + // Update the latest entry state (latest is the entry with largest clock time) + this._replicationStatus.queued ++ + const max = entry.clock ? entry.clock.time : 0 + this._recalculateReplicationMax(max) + // logger.debug(``) + this.emit('replicate', this.address.toString(), entry) + } + + async _onLoadCompleted (logs, have) { + try { + for (let log of logs) { + await this._oplog.join(log) } - this._replicator.on('load.end', onLoadCompleted) + this._replicationStatus.queued -= logs.length + this._replicationStatus.buffered = this._replicator._buffer.length + await this._updateIndex() + + //only store heads that has been verified and merges + const heads = this._oplog.heads + await this._cache.set('_remoteHeads', heads) + logger.debug(`Saved heads ${heads.length} [${heads.map(e => e.hash).join(', ')}]`) + + // logger.debug(``) + this.emit('replicated', this.address.toString(), logs.length) } catch (e) { console.error("Store Error:", e) } @@ -185,7 +180,7 @@ class Store extends EventEmitter { await this._cache.destroy() // Reset this._index = new this.options.Index(this.uid) - this._oplog = new Log(this._ipfs, this.id, null, null, null, this._key, this.access.write) + this._oplog = new Log(this._ipfs, this.address.toString(), null, null, null, this._key, this.access.write) this._cache = this.options.cache } @@ -439,7 +434,7 @@ class Store extends EventEmitter { this._oplog.length, max || 0, ]) - this._recalculateReplicationMax(this.replicationStatus.progress) + this._recalculateReplicationMax(this._replicationStatus.progress) } _recalculateReplicationMax (max) { From fc16b0f7a6420a00718422066c27d28319241fca Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 14:13:41 -0300 Subject: [PATCH 5/8] Add initialized event * This is useful for subscribing to pubsub using the store parameters and adding the store to orbit stores property --- src/Store.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/Store.js b/src/Store.js index c68c387..15f97ca 100644 --- a/src/Store.js +++ b/src/Store.js @@ -77,6 +77,8 @@ class Store extends EventEmitter { this._replicator.on('load.added', this._onLoadAdded.bind(this)) this._replicator.on('load.progress', this._onReplicatorLoadProgress.bind(this)) this._replicator.on('load.end', this._onLoadCompleted.bind(this)) + + this.emit('initialized', this) } _onReplicatorLoadProgress(id, hash, entry, have, bufferedLength) { From 02401d7d192e81f9cc1ad11a8871786e3d8f346b Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 15:26:33 -0300 Subject: [PATCH 6/8] Add SnapshotManager --- src/Store.js | 146 +++++++------------------------------- src/snapshot-manager.js | 153 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 180 insertions(+), 119 deletions(-) create mode 100644 src/snapshot-manager.js diff --git a/src/Store.js b/src/Store.js index 15f97ca..77023fa 100644 --- a/src/Store.js +++ b/src/Store.js @@ -1,11 +1,11 @@ 'use strict' const EventEmitter = require('events').EventEmitter -const Readable = require('readable-stream') const mapSeries = require('p-each-series') const Log = require('ipfs-log') const Logger = require('logplease') +const SnapshotManager = require('./snapshot-manager') const StoreIndex = require('./Index') const Replicator = require('./Replicator') const ReplicationInfo = require('./replication-info') @@ -77,6 +77,7 @@ class Store extends EventEmitter { this._replicator.on('load.added', this._onLoadAdded.bind(this)) this._replicator.on('load.progress', this._onReplicatorLoadProgress.bind(this)) this._replicator.on('load.end', this._onLoadCompleted.bind(this)) + this._snapshotManager = new SnapshotManager(this._ipfs, this, this._cache, this._replicator) this.emit('initialized', this) } @@ -265,136 +266,43 @@ class Store extends EventEmitter { async saveSnapshot () { const unfinished = this._replicator.getQueue() - - let snapshotData = this._oplog.toSnapshot() - let header = new Buffer(JSON.stringify({ - id: snapshotData.id, - heads: snapshotData.heads, - size: snapshotData.values.length, - type: this.type, - })) - const rs = new Readable() - let size = new Uint16Array([header.length]) - let bytes = new Buffer(size.buffer) - rs.push(bytes) - rs.push(header) - - const addToStream = (val) => { - let str = new Buffer(JSON.stringify(val)) - let size = new Uint16Array([str.length]) - rs.push(new Buffer(size.buffer)) - rs.push(str) - } - - snapshotData.values.forEach(addToStream) - rs.push(null) // tell the stream we're finished - - const snapshot = await this._ipfs.files.add(rs) - - await this._cache.set('snapshot', snapshot[snapshot.length - 1]) - await this._cache.set('queue', unfinished) - - logger.debug(`Saved snapshot: ${snapshot[snapshot.length - 1].hash}, queue length: ${unfinished.length}`) - - return snapshot + return this._snapshotManager.saveSnapshot(this._ipfs, this._oplog, unfinished, this._type) } - async loadFromSnapshot (onProgressCallback) { + async loadFromSnapshot () { this.emit('load', this.address.toString()) - const maxClock = (res, val) => Math.max(res, val.clock.time) const queue = await this._cache.get('queue') this.sync(queue || []) - const snapshot = await this._cache.get('snapshot') + const snapshot = await this._snapshotManager.loadSnapshot(this._ipfs, this._cache, queue, this.address) if (snapshot) { - const res = await this._ipfs.files.catReadableStream(snapshot.hash) - const loadSnapshotData = () => { - return new Promise((resolve, reject) => { - let buf = new Buffer(0) - let q = [] - - const bufferData = (d) => { - this._byteSize += d.length - if (q.length < 20000) { - q.push(d) - } else { - const a = Buffer.concat(q) - buf = Buffer.concat([buf, a]) - q = [] - } - } - - const done = () => { - if (q.length > 0) { - const a = Buffer.concat(q) - buf = Buffer.concat([buf, a]) - } - - function toArrayBuffer (buf) { - var ab = new ArrayBuffer(buf.length) - var view = new Uint8Array(ab) - for (var i = 0; i < buf.length; ++i) { - view[i] = buf[i] - } - return ab - } - - const headerSize = parseInt(new Uint16Array(toArrayBuffer(buf.slice(0, 2)))) - let header - - try { - header = JSON.parse(buf.slice(2, headerSize + 2)) - } catch (e) { - // TODO - } - - let values = [] - let a = 2 + headerSize - while (a < buf.length) { - const s = parseInt(new Uint16Array(toArrayBuffer(buf.slice(a, a + 2)))) - a += 2 - const data = buf.slice(a, a + s) - try { - const d = JSON.parse(data) - values.push(d) - } catch (e) { - } - a += s - } - - if (header) { - this._type = header.type - resolve({ values: values, id: header.id, heads: header.heads, type: header.type }) - } else { - resolve({ values: values, id: null, heads: null, type: null }) - } - } - res.on('data', bufferData) - res.on('end', done) - }) - } - - const onProgress = (hash, entry, count, total) => { - this._recalculateReplicationStatus(count, entry.clock.time) - this._onLoadProgress(hash, entry) - } - + const maxClock = (res, val) => Math.max(res, val.clock.time) + this._recalculateReplicationMax(snapshot.values.reduce(maxClock, 0)) // Fetch the entries // Timeout 1 sec to only load entries that are already fetched (in order to not get stuck at loading) - const snapshotData = await loadSnapshotData() - this._recalculateReplicationMax(snapshotData.values.reduce(maxClock, 0)) - if (snapshotData) { - const log = await Log.fromJSON(this._ipfs, snapshotData, -1, this._key, this.access.write, 1000, onProgress) - await this._oplog.join(log) - await this._updateIndex() - this.emit('replicated', this.address.toString()) - } - this.emit('ready', this.address.toString(), this._oplog.heads) - } else { - throw new Error(`Snapshot for ${this.address} not found!`) + const length = -1 + const timeout = 1000 + const log = await Log.fromJSON( + this._ipfs, + snapshot, + length, + this._key, + this.access.write, + timeout, + (hash, entry, count) => { + this._recalculateReplicationStatus(count, entry.clock.time) + this._onLoadProgress(hash, entry) + } + ) + + await this._oplog.join(log) + await this._updateIndex() + this.emit('replicated', this.address.toString()) } + this.emit('ready', this.address.toString(), this._oplog.heads) + return this } diff --git a/src/snapshot-manager.js b/src/snapshot-manager.js new file mode 100644 index 0000000..d2850b5 --- /dev/null +++ b/src/snapshot-manager.js @@ -0,0 +1,153 @@ +'use strict' + +const Log = require('ipfs-log') +const Logger = require('logplease') +const ReadableStream = require('readable-stream') + +const logger = Logger.create('orbit-db.store.snapshotManager', { color: Logger.Colors.Blue }) +Logger.setLogLevel('ERROR') + +const toArrayBuffer = (buf) => { + const ab = new ArrayBuffer(buf.length) + const view = new Uint8Array(ab) + for (var i = 0; i < buf.length; ++i) { + view[i] = buf[i] + } + + return ab +} + +const addToStream = (rs, val) => { + const str = new Buffer(JSON.stringify(val)) + const size = new Uint16Array([str.length]) + rs.push(new Buffer(size.buffer)) + rs.push(str) +} + +class SnapshotManager { + constructor(ipfs, store, cache, replicator) { + super() + + if (!ipfs) throw new Error('Ipfs instance not defined') + if (!store) throw new Error('Store instance not defined') + if (!cache) throw new Error('Cache instance not defined') + if (!replicator) throw new Error('Replicator instance not defined') + + this._ipfs = ipfs + this._store = store + cache = cache + this._replicator = replicator + } + + async saveSnapshot (ipfs, log, unfinished, storeType) { + if (!ipfs) throw new Error('Ipfs instance not defined, could not save snapshot') + if (!log) throw new Error('Oplog not defined, could not save snapshot') + if (!storeType) throw new Error('Store type not defined, could not save snapshot') + + const snapshotData = log.toSnapshot() + const header = Buffer.from(JSON.stringify({ + id: snapshotData.id, + heads: snapshotData.heads, + size: snapshotData.values.length, + type: storeType, + })) + + const stream = new ReadableStream() + const size = new Uint16Array([header.length]) + const padding = new Buffer(size.buffer) + stream.push(padding) + stream.push(header) + snapshotData.values.forEach(addToStream) + stream.push(null) // tell the stream we're finished + + const snapshot = await this._ipfs.files.add(rs) + await cache.set('snapshot', snapshot[snapshot.length - 1]) + await cache.set('queue', unfinished) + + logger.debug(`Saved snapshot: ${snapshot[snapshot.length - 1].hash}, queue length: ${unfinished.length}`) + + return snapshot + } + + _parseSnapshotHeader (buffer) { + const headerSize = parseInt(new Uint16Array(toArrayBuffer(buffer.slice(0, 2)))) + const offset = 2 + let header + try { + header = JSON.parse(buffer.slice(offset, headerSize + offset)) + } catch (e) { + // TODO: Decide how to handle JSON parsing errors here + } + + return { + header, + size: headerSize + } + } + + _parseSnapshotBody (headerSize, buffer) { + const values = [] + const padding = 2 + const offset = padding + headerSize + + while (offset < buffer.length) { + const length = parseInt(new Uint16Array(toArrayBuffer(buffer.slice(offset, offset + padding)))) + offset += padding + try { + const chunk = buffer.slice(offset, offset + length) + const data = JSON.parse(chunk) + values.push(data) + } catch (e) { + // TODO: Decide how to handle JSON parsing errors here + } + offset += length + } + + return values + } + + async _parseSnapshotDataStream (stream) { + return new Promise((resolve, reject) => { + let buffer = new Buffer(0) + let queue = [] + const watermark = 20000 + const bufferData = data => { + if (queue.length < watermark) { + queue.push(data) + } else { + const enqueued = Buffer.concat(queue) + buffer = Buffer.concat([buffer, enqueued]) + queue = [] + } + } + + const done = () => { + if (queue.length > 0) { + const enqueued = Buffer.concat(queue) + buffer = Buffer.concat([buffer, enqueued]) + } + + const { header, size: headerSize } = this._parseSnapshotHeader(buffer) + const values = this._parseSnapshotBody(headerSize, buffer) + if (header) { + const { heads, id, type } = header + resolve({ values, id, heads, type }) + } else { + resolve({ values, id: null, heads: null, type: null }) + } + } + + stream.on('data', bufferData) + stream.on('end', done) + }) + } + + async loadSnapshot (ipfs, cache, queue, address) { + const snapshot = await cache.get('snapshot') + if (!snapshot) throw new Error(`Snapshot for ${address} not found!`) + const stream = await ipfs.files.catReadableStream(snapshot.hash) + return this._parseSnapshotDataStream(stream) + } +} + +module.exports = SnapshotManager From 73a10bdad00d5c6dd6c4793ed87a15797b293867 Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 15:34:50 -0300 Subject: [PATCH 7/8] fixup! Add SnapshotManager --- src/Store.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Store.js b/src/Store.js index 77023fa..b25ad39 100644 --- a/src/Store.js +++ b/src/Store.js @@ -273,7 +273,7 @@ class Store extends EventEmitter { this.emit('load', this.address.toString()) const queue = await this._cache.get('queue') - this.sync(queue || []) + await this.sync(queue || []) const snapshot = await this._snapshotManager.loadSnapshot(this._ipfs, this._cache, queue, this.address) if (snapshot) { From 8771ba9b52f8e9a90ca29e7a8812d5b49c61b606 Mon Sep 17 00:00:00 2001 From: thiagodelgado111 Date: Tue, 4 Sep 2018 15:34:04 -0300 Subject: [PATCH 8/8] Move cache to Store --- package-lock.json | 471 ++++++++++++++++++++++++++++++++++++++++++++++ package.json | 1 + src/Store.js | 24 +++ 3 files changed, 496 insertions(+) diff --git a/package-lock.json b/package-lock.json index 0af4940..687d694 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,16 +4,172 @@ "lockfileVersion": 1, "requires": true, "dependencies": { + "abstract-leveldown": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/abstract-leveldown/-/abstract-leveldown-5.0.0.tgz", + "integrity": "sha512-5mU5P1gXtsMIXg65/rsYGsi93+MlogXZ9FA8JnwKurHQg64bfXwGYVdVdijNTVNOlAsuIiOwHdvFFD5JqCJQ7A==", + "requires": { + "xtend": "~4.0.0" + } + }, + "ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" + }, + "aproba": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", + "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==" + }, + "are-we-there-yet": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.5.tgz", + "integrity": "sha512-5hYdAkZlcG8tOLujVDTgCT+uPX0VnpAH28gWsLfzpXYm7wP6mp5Q/gYyR7YQ0cKVJcXJnl3j2kpBan13PtQf6w==", + "requires": { + "delegates": "^1.0.0", + "readable-stream": "^2.0.6" + } + }, + "bindings": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.3.0.tgz", + "integrity": "sha512-DpLh5EzMR2kzvX1KIlVC0VkC3iZtHKTgdtZ0a3pglBZdaQFjt5S9g9xd1lE+YvXyfd6mtCeRnrUfOLYiTMlNSw==" + }, + "bl": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/bl/-/bl-1.2.2.tgz", + "integrity": "sha512-e8tQYnZodmebYDWGH7KMRvtzKXaJHx3BbilrgZCfvyLUYdKpK1t5PSPmpkny/SgiTSCnjfLW7v5rlONXVFkQEA==", + "requires": { + "readable-stream": "^2.3.5", + "safe-buffer": "^5.1.1" + } + }, + "buffer-alloc": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/buffer-alloc/-/buffer-alloc-1.2.0.tgz", + "integrity": "sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow==", + "requires": { + "buffer-alloc-unsafe": "^1.1.0", + "buffer-fill": "^1.0.0" + } + }, + "buffer-alloc-unsafe": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz", + "integrity": "sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg==" + }, + "buffer-fill": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/buffer-fill/-/buffer-fill-1.0.0.tgz", + "integrity": "sha1-+PeLdniYiO858gXNY39o5wISKyw=" + }, + "chownr": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.0.1.tgz", + "integrity": "sha1-4qdQQqlVGQi+vSW4Uj1fl2nXkYE=" + }, + "code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" + }, + "console-control-strings": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", + "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=" + }, "core-util-is": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" }, + "decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", + "requires": { + "mimic-response": "^1.0.0" + } + }, + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==" + }, + "delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=" + }, + "detect-libc": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-1.0.3.tgz", + "integrity": "sha1-+hN8S9aY7fVc1c0CrFWfkaTEups=" + }, + "end-of-stream": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.1.tgz", + "integrity": "sha512-1MkrZNvWTKCaigbn+W15elq2BB/L22nqrSY5DKlo3X6+vclJm8Bb5djXJBmEX6fS3+zCh/F4VBK5Z2KxJt4s2Q==", + "requires": { + "once": "^1.4.0" + } + }, + "expand-template": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-1.1.1.tgz", + "integrity": "sha512-cebqLtV8KOZfw0UI8TEFWxtczxxC1jvyUvx6H4fyp1K1FN7A4Q+uggVUlOsI1K8AGU0rwOGqP8nCapdrw8CYQg==" + }, + "fast-future": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/fast-future/-/fast-future-1.0.2.tgz", + "integrity": "sha1-hDWpqqAteSSNF9cE52JZMB2ZKAo=" + }, + "fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==" + }, + "gauge": { + "version": "2.7.4", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", + "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", + "requires": { + "aproba": "^1.0.3", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.0", + "object-assign": "^4.1.0", + "signal-exit": "^3.0.0", + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wide-align": "^1.1.0" + } + }, + "github-from-package": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/github-from-package/-/github-from-package-0.0.0.tgz", + "integrity": "sha1-l/tdlr/eiXMxPyDoKI75oWf6ZM4=" + }, + "has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=" + }, + "immediate": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/immediate/-/immediate-3.2.3.tgz", + "integrity": "sha1-0UD6j2FGWb1lQSMwl92qwlzdmRw=" + }, "inherits": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, + "ini": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", + "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==" + }, "ipfs-log": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/ipfs-log/-/ipfs-log-4.1.2.tgz", @@ -23,16 +179,156 @@ "p-whilst": "^1.0.0" } }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" + }, "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" }, + "level-js": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/level-js/-/level-js-3.0.0.tgz", + "integrity": "sha512-e2dVpjCWNwIcyboZUsLqx2vERM0I5OPZOE9wfD22fk8b8OeuZRoV4scr0Y+YIyDXE5cwOsO/1LyjsdJ36o+9Ag==", + "requires": { + "abstract-leveldown": "~5.0.0", + "immediate": "~3.2.3", + "inherits": "^2.0.3", + "ltgt": "^2.1.2", + "typedarray-to-buffer": "~3.1.5" + } + }, + "leveldown": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/leveldown/-/leveldown-3.0.2.tgz", + "integrity": "sha512-+ANRScj1npQQzv6e4DYAKRjVQZZ+ahMoubKrNP68nIq+l9bYgb+WiXF+14oTcQTg2f7qE9WHGW7rBG9nGSsA+A==", + "requires": { + "abstract-leveldown": "~4.0.0", + "bindings": "~1.3.0", + "fast-future": "~1.0.2", + "nan": "~2.10.0", + "prebuild-install": "^4.0.0" + }, + "dependencies": { + "abstract-leveldown": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/abstract-leveldown/-/abstract-leveldown-4.0.3.tgz", + "integrity": "sha512-qsIHFQy0u17JqSY+3ZUT+ykqxYY17yOfvAsLkFkw8kSQqi05d1jyj0bCuSX6sjYlXuY9cKpgUt5EudQdP4aXyA==", + "requires": { + "xtend": "~4.0.0" + } + } + } + }, "logplease": { "version": "1.2.14", "resolved": "https://registry.npmjs.org/logplease/-/logplease-1.2.14.tgz", "integrity": "sha512-n6bf1Ce0zvcmuyOzDi2xxLix6F1D/Niz7Qa4K3BmkjyaXcovzEjwZKUYsV+0F2Uv4rlXm5cToIEB+ynqSRdwGw==" }, + "ltgt": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/ltgt/-/ltgt-2.2.1.tgz", + "integrity": "sha1-81ypHEk/e3PaDgdJUwTxezH4fuU=" + }, + "mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" + }, + "minimist": { + "version": "1.2.0", + "resolved": "http://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" + }, + "mkdirp": { + "version": "0.5.1", + "resolved": "http://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", + "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", + "requires": { + "minimist": "0.0.8" + }, + "dependencies": { + "minimist": { + "version": "0.0.8", + "resolved": "http://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", + "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + } + } + }, + "nan": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", + "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" + }, + "node-abi": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/node-abi/-/node-abi-2.4.3.tgz", + "integrity": "sha512-b656V5C0628gOOA2kwcpNA/bxdlqYF9FvxJ+qqVX0ctdXNVZpS8J6xEUYir3WAKc7U0BH/NRlSpNbGsy+azjeg==", + "requires": { + "semver": "^5.4.1" + } + }, + "noop-logger": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/noop-logger/-/noop-logger-0.1.1.tgz", + "integrity": "sha1-lKKxYzxPExdVMAfYlm/Q6EG2pMI=" + }, + "npmlog": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.2.tgz", + "integrity": "sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==", + "requires": { + "are-we-there-yet": "~1.1.2", + "console-control-strings": "~1.1.0", + "gauge": "~2.7.3", + "set-blocking": "~2.0.0" + } + }, + "number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" + }, + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" + }, + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", + "requires": { + "wrappy": "1" + } + }, + "orbit-db-cache": { + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/orbit-db-cache/-/orbit-db-cache-0.2.4.tgz", + "integrity": "sha512-0Z0t6C948UOLr7YqZd6opmaCuzCNXFrNS5yG37S4GOJmqZbUi4EuwsqPOX53v4/0fNMsVa18U1ocyHfSShb4+Q==", + "requires": { + "level-js": "~3.0.0", + "leveldown": "~3.0.2", + "logplease": "^1.2.14", + "mkdirp": "^0.5.1" + } + }, + "os-homedir": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", + "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" + }, "p-each-series": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-each-series/-/p-each-series-1.0.0.tgz", @@ -56,11 +352,53 @@ "resolved": "https://registry.npmjs.org/p-whilst/-/p-whilst-1.0.0.tgz", "integrity": "sha1-VGaOrX+TR5n8APHlIw/Wrd645+Y=" }, + "prebuild-install": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/prebuild-install/-/prebuild-install-4.0.0.tgz", + "integrity": "sha512-7tayxeYboJX0RbVzdnKyGl2vhQRWr6qfClEXDhOkXjuaOKCw2q8aiuFhONRYVsG/czia7KhpykIlI2S2VaPunA==", + "requires": { + "detect-libc": "^1.0.3", + "expand-template": "^1.0.2", + "github-from-package": "0.0.0", + "minimist": "^1.2.0", + "mkdirp": "^0.5.1", + "node-abi": "^2.2.0", + "noop-logger": "^0.1.1", + "npmlog": "^4.0.1", + "os-homedir": "^1.0.1", + "pump": "^2.0.1", + "rc": "^1.1.6", + "simple-get": "^2.7.0", + "tar-fs": "^1.13.0", + "tunnel-agent": "^0.6.0", + "which-pm-runs": "^1.0.0" + } + }, "process-nextick-args": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" }, + "pump": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/pump/-/pump-2.0.1.tgz", + "integrity": "sha512-ruPMNRkN3MHP1cWJc9OWr+T/xDP0jhXYCLfJcBuX54hhfIBnaQmAUMfDcG4DM5UMWByBbJY69QSphm3jtDKIkA==", + "requires": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "requires": { + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + } + }, "readable-stream": { "version": "2.3.6", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", @@ -80,6 +418,46 @@ "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" }, + "semver": { + "version": "5.5.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", + "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==" + }, + "set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" + }, + "signal-exit": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" + }, + "simple-concat": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", + "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" + }, + "simple-get": { + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", + "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", + "requires": { + "decompress-response": "^3.3.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" + } + }, + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, "string_decoder": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", @@ -88,10 +466,103 @@ "safe-buffer": "~5.1.0" } }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "requires": { + "ansi-regex": "^2.0.0" + } + }, + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=" + }, + "tar-fs": { + "version": "1.16.3", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-1.16.3.tgz", + "integrity": "sha512-NvCeXpYx7OsmOh8zIOP/ebG55zZmxLE0etfWRbWok+q2Qo8x/vOR/IJT1taADXPe+jsiu9axDb3X4B+iIgNlKw==", + "requires": { + "chownr": "^1.0.1", + "mkdirp": "^0.5.1", + "pump": "^1.0.0", + "tar-stream": "^1.1.2" + }, + "dependencies": { + "pump": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/pump/-/pump-1.0.3.tgz", + "integrity": "sha512-8k0JupWme55+9tCVE+FS5ULT3K6AbgqrGa58lTT49RpyfwwcGedHqaC5LlQNdEAumn/wFsu6aPwkuPMioy8kqw==", + "requires": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + } + } + }, + "tar-stream": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.6.1.tgz", + "integrity": "sha512-IFLM5wp3QrJODQFPm6/to3LJZrONdBY/otxcvDIQzu217zKye6yVR3hhi9lAjrC2Z+m/j5oDxMPb1qcd8cIvpA==", + "requires": { + "bl": "^1.0.0", + "buffer-alloc": "^1.1.0", + "end-of-stream": "^1.0.0", + "fs-constants": "^1.0.0", + "readable-stream": "^2.3.0", + "to-buffer": "^1.1.0", + "xtend": "^4.0.0" + } + }, + "to-buffer": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.1.1.tgz", + "integrity": "sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg==" + }, + "tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "requires": { + "safe-buffer": "^5.0.1" + } + }, + "typedarray-to-buffer": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", + "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", + "requires": { + "is-typedarray": "^1.0.0" + } + }, "util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" + }, + "which-pm-runs": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/which-pm-runs/-/which-pm-runs-1.0.0.tgz", + "integrity": "sha1-Zws6+8VS4LVd9rd4DKdGFfI60cs=" + }, + "wide-align": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.3.tgz", + "integrity": "sha512-QGkOQc8XL6Bt5PwnsExKBPuMKBxnGxWWW3fU55Xt4feHozMUhdUMaBCk290qpm/wG5u/RSKzwdAC4i51YigihA==", + "requires": { + "string-width": "^1.0.2 || 2" + } + }, + "wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" + }, + "xtend": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.1.tgz", + "integrity": "sha1-pcbVMr5lbiPbgg77lDofBJmNY68=" } } } diff --git a/package.json b/package.json index de47a42..4acf4d8 100644 --- a/package.json +++ b/package.json @@ -18,6 +18,7 @@ "dependencies": { "ipfs-log": "~4.1.0", "logplease": "^1.2.14", + "orbit-db-cache": "^0.2.4", "p-each-series": "^1.0.0", "readable-stream": "~2.3.5" } diff --git a/src/Store.js b/src/Store.js index b25ad39..a41d963 100644 --- a/src/Store.js +++ b/src/Store.js @@ -4,6 +4,7 @@ const EventEmitter = require('events').EventEmitter const mapSeries = require('p-each-series') const Log = require('ipfs-log') const Logger = require('logplease') +const Cache = require('orbit-db-cache') const SnapshotManager = require('./snapshot-manager') const StoreIndex = require('./Index') @@ -121,6 +122,29 @@ class Store extends EventEmitter { } } + static async loadCache(path, address) { + let cache + try { + cache = await Cache.load(path, address) + } catch (e) { + console.error(e) + logger.error(`Couldn't load Cache: ${e}`) + } + + return cache + } + + static async loadManifest(path, address) { + const cache = await Store.loadCache(path, address) + return cache.get(path.join(address.toString(), '_manifest')) + } + + static async saveManifest(path, address) { + const cache = await Store.loadCache(path, address) + await cache.set(path.join(address.toString(), '_manifest'), address.root) + logger.debug(`Saved manifest to IPFS as '${address.root}'`) + } + get all () { return Array.isArray(this._index._index) ? this._index._index