Exception on connect promise with lovefield

707 Views Asked by At

the exception thrown:
lovefield.js:2113 Uncaught NotFoundError: Failed to execute 'transaction' on 'IDBDatabase': One of the specified object stores was not found.

Ello folks, I've been fighting with Lovefied for quite some time attempting to get my db schema initialized. I've wrapped everything in try catch blocks that I suspected there could be an issue and haven't gotten anything there. I've tracked it down to the lovefield function throwing the exception.scanRowId_ but, I'm still at a loss as to what is causing this. If it were something as straight forward as missing tables or missing fields It should have broke something on the way. Any thought on what is the cause?


Exibit 1: lovelace source code

the section that reads : try { var tx = opt_tx || db.transaction([tableName]); req = tx.objectStore(tableName).openCursor(null, "prev"); } catch (e) { reject(e); return; } is where the exception is being thrown.

lf.backstore.IndexedDB.prototype.scanRowId_ = function(opt_tx) {
  var tableNames = this.schema_.tables().map(function(table) {
    return table.getName();
  }), db = this.db_, maxRowId = 0, extractRowId = function(cursor) {
    if (this.bundledMode_) {
      var page = lf.backstore.Page.deserialize(cursor.value);
      return Object.keys(page.getPayload()).reduce(function(prev, cur) {
        return Math.max(prev, cur);
      }, 0);
    }
    return cursor.key;
  }.bind(this), scanTableRowId = function(tableName) {
    return new goog.Promise(function(resolve, reject) {
      var req;
      try {
        var tx = opt_tx || db.transaction([tableName]);
        req = tx.objectStore(tableName).openCursor(null, "prev");
      } catch (e) {
        reject(e);
        return;
      }
      req.onsuccess = function(ev) {
        var cursor = ev.target.result;
        cursor && (maxRowId = Math.max(maxRowId, extractRowId(cursor)));
        resolve(maxRowId);
      };
      req.onerror = function() {
        resolve(maxRowId);
      };
    });
  }, execSequentially = function() {
    if (0 == tableNames.length) {
      return goog.Promise.resolve();
    }
    var tableName = tableNames.shift();
    return scanTableRowId(tableName).then(execSequentially);
  };
  return new goog.Promise(function(resolve) {
    execSequentially().then(function() {
      resolve(maxRowId);
    });
  });
};

Exibit 2: The code that builds the db schema

    var buildSchema = function() {

        schemaBuilder = lf.schema.create(urlConfig.dsName, urlConfig.versionNumber);
        console.assert(tableSchemas, 'tableSchemas!=null');
        console.assert(schemaBuilder, 'schemaBuilder!=null');

        angular.forEach(tableSchemas, function(val, key) {

            var item = tableSchemas[key];
            console.assert(item, 'item should not be null');

            var tableName = item['tsName'];
            console.assert(tableName, 'tableName should not be null');

            var fields = item['metaRecords'];
            console.assert(fields, 'fields should not be null');
            var table;

            var isPrimary = '';
            try {
                table = schemaBuilder.createTable(tableName);
            } catch (error) {
                console.log('failed to createTable(' + tableName + ')');
                console.log(error);
            }

            for (var x = 0; x < fields.length; x++) {
                var field = fields[x];
                try {
                    table.addColumn(field['fieldName'], eval(field['dataType']));
                } catch (error) {
                    console.log('failed at table.addColumn(' + field['fieldName'] + ',' + eval(field['dataType']) + ')');
                    console.log(error);
                }
                try {
                    if (field['isPrimary'] === '1') {
                        isPrimary = field['fieldName'];
                    } else {
                        table.addNullable([field['fieldName']]);
                    }
                } catch (error) {
                    console.log('failed at table.addNullable(' + field['fieldName']);
                    console.log(error);
                }
            }

            try {
                if (isPrimary !== '') {
                    if (isPrimary === 'autoid') {
                        table.addPrimaryKey([isPrimary], true);
                    } else {
                        table.addPrimaryKey([isPrimary]);
                    }
                }
            } catch (error) {
                console.log('failed at table.addPrimaryKey('+ [isPrimary]+')');
                console.log(error);
            }

        });
        //
        persistservice.setVal('dbInitialized', true);

    };

Exibit 3: The code that breaks on

Specificly, the break happens at the promise return.

return schemaBuilder.connect().then(function(db) {

/**
 * Instantiates the DB connection (re-entrant).
 * @return {!IThenable<!lf.Database>}
 */
var getDbConnection = function() {
    if (db_ != null) {
        return db_;
    }

    if (!schemaBuilder) {
        buildSchema();
    }

    return schemaBuilder.connect()
        .then(function(db) {
            db_ = db;
            op = lovefield.op;
            fn = lovefield.fn;
            lf = lf;
            onConnected_();
            return db;
        });
};

Exibit 4: The stack trace

Uncaught NotFoundError: Failed to execute 'transaction' on 'IDBDatabase': One of the specified object stores was not found.(anonymous function) @

The stacktrace: lovefield.js:2113setTimeout (async)goog.async.throwException @ lovefield.js:2112(anonymous function) @ lovefield.js:2589goog.async.run.processWorkQueue @ lovefield.js:2250Promise.resolve (async)goog.async.run.schedule_ @ lovefield.js:2227goog.async.run @ lovefield.js:2220goog.Promise.scheduleCallbacks_ @ lovefield.js:2515goog.Promise.resolve_ @ lovefield.js:2480(anonymous function) @ lovefield.js:2302(anonymous function) @ lovefield.js:6393goog.Promise @ lovefield.js:2290scanTableRowId @ lovefield.js:6387execSequentially @ lovefield.js:6410(anonymous function) @ lovefield.js:6413goog.Promise @ lovefield.js:2290lf.backstore.IndexedDB.scanRowId_ @ lovefield.js:6412(anonymous function) @ lovefield.js:6316IndexedDB (async)(anonymous function) @ lovefield.js:6301goog.Promise @ lovefield.js:2290lf.backstore.IndexedDB.init @ lovefield.js:6298lf.base.init @ lovefield.js:11246lf.proc.Database.init @ lovefield.js:11548lf.schema.Builder.connect @ lovefield.js:12202getDbConnection @ lovefieldservice.js:181lovefieldService @ lovefieldservice.js:194instantiate @ angular.js:4619(anonymous function) @ angular.js:4459invoke @ angular.js:4604enforcedReturnValue @ angular.js:4443invoke @ angular.js:4604(anonymous function) @ angular.js:4403getService @ angular.js:4550injectionArgs @ angular.js:4574instantiate @ angular.js:4616(anonymous function) @ angular.js:9870(anonymous function) @ angular-ui-router.js:4081invokeLinkFn @ angular.js:9492nodeLinkFn @ angular.js:8978compositeLinkFn @ angular.js:8226publicLinkFn @ angular.js:8106(anonymous function) @ angular.js:8447updateView @ angular-ui-router.js:4021(anonymous function) @ angular-ui-router.js:3959Scope.$broadcast @ angular.js:17143$state.transition.resolved.then.$state.transition @ angular-ui-router.js:3352processQueue @ angular.js:15552(anonymous function) @ angular.js:15568Scope.$eval @ angular.js:16820Scope.$digest @ angular.js:16636Scope.$apply @ angular.js:16928done @ angular.js:11266completeRequest @ angular.js:11464requestLoaded @ angular.js:11405XMLHttpRequest.send (async)(anonymous function) @ angular.js:11442sendReq @ angular.js:11235serverRequest @ angular.js:10945processQueue @ angular.js:15552(anonymous function) @ angular.js:15568Scope.$eval @ angular.js:16820Scope.$digest @ angular.js:16636Scope.$apply @ angular.js:16928bootstrapApply @ angular.js:1694invoke @ angular.js:4604doBootstrap @ angular.js:1692bootstrap @ angular.js:1712angularInit @ angular.js:1606(anonymous function) @ angular.js:30423fire @ jquery.js:3182self.fireWith @ jquery.js:3312jQuery.extend.ready @ jquery.js:3531completed @ jquery.js:3547

1

There are 1 best solutions below

0
On BEST ANSWER

Okay folk, I just cleared out my IndexedDB data store with indexedDB.deleteDatabase('adDB'); and that fixed it right up. Derp on me for that. It was picking up all my tables but one for some reason prior. (Probably because the db threw an error and finalized on a previous revision before I got through all the tables in the array. When in doubt clear it out!!!

Also kudos on this answer for how to clear out you indexedDb data store. How to delete indexedDB in Chrome