feat: save/restore database snapshots (#78)

This commit is contained in:
Richard Ramos 2020-03-20 12:56:57 -04:00 committed by GitHub
parent e9c71c1d71
commit ada876dec7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 44 additions and 8 deletions

View File

@ -41,9 +41,8 @@ class Database {
}
databaseInitialize(cb) {
// TODO: save in the db results by using a combination of concatMap and scan, to save results in batches
fromEvent(this.events, "updateDB").subscribe(({eventKey, eventData}) => {
if (eventData.removed) {
if (eventData.removed) {
this.deleteEvent(eventKey, eventData.id);
return;
}
@ -56,6 +55,25 @@ class Database {
});
}
serialize() {
return this.db.serialize();
}
restore(serializedDb, forced) {
return new Promise((resolve, reject) => {
const collections = this.db.listCollections();
if (!collections?.length || forced) {
this.db.loadJSON(serializedDb);
this.db.saveDatabase(err => {
if(err) {
reject(err);
}
resolve();
});
}
});
}
getLastKnownEvent(eventKey) {
const collection = this.db.getCollection(eventKey);
if (collection?.count()) {
@ -99,9 +117,10 @@ class Database {
deleteEvent(eventKey, eventId) {
const collection = this.db.getCollection(eventKey);
if (collection)
collection.chain()
.find({id: eventId})
.remove();
collection
.chain()
.find({id: eventId})
.remove();
}
deleteNewestBlocks(eventKey, gteBlockNum) {
@ -109,9 +128,10 @@ class Database {
const collection = this.db.getCollection(eventKey);
if (collection)
collection.chain()
.find({blockNumber: {$gte: gteBlockNum}})
.remove();
collection
.chain()
.find({blockNumber: {$gte: gteBlockNum}})
.remove();
}
}

View File

@ -33,6 +33,7 @@ export default class Subspace {
this.options.callInterval = options.callInterval;
this.options.dbFilename = options.dbFilename ?? "subspace.db";
this.options.disableDatabase = options.disableDatabase;
this.options.snapshot = options.snapshot;
this.networkId = undefined;
this.isWebsocketProvider = options.disableSubscriptions ? false : !!web3?.currentProvider?.on;
@ -44,6 +45,11 @@ export default class Subspace {
} else {
this._db = new Database(this.options.dbFilename, this.events);
}
if(this.options.snapshot) {
await this._db.restore(this.options.snapshot);
}
this.eventSyncer = new EventSyncer(this.web3.eth, this.events, this._db, this.isWebsocketProvider);
this.logSyncer = new LogSyncer(this.web3.eth, this.events, this._db);
@ -308,4 +314,12 @@ export default class Subspace {
close() {
this.eventSyncer.close();
}
snapshot() {
return this._db.serialize();
}
async loadSnapshot(serializedDb) {
return this._db.restore(serializedDb, true);
}
}

View File

@ -19,6 +19,8 @@ export default class Subspace {
trackGasPrice(): Observable<string>;
trackAverageBlocktime(): Observable<number>;
close(): void;
snapshot(): string;
async loadSnapshot(serializedDb: string): void;
}
export interface ContractLike {