requestTransaction accepts Promises&Generators
This commit is contained in:
		
							parent
							
								
									8d1bccbea0
								
							
						
					
					
						commit
						6f99ee5c34
					
				@ -8,6 +8,7 @@
 | 
				
			|||||||
  },
 | 
					  },
 | 
				
			||||||
  "parser": "babel-eslint",
 | 
					  "parser": "babel-eslint",
 | 
				
			||||||
  "globals": {
 | 
					  "globals": {
 | 
				
			||||||
        "OperationBuffer": true
 | 
					        "OperationBuffer": true,
 | 
				
			||||||
 | 
					        "IndexedDB": true
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										67
									
								
								gulpfile.js
									
									
									
									
									
								
							
							
						
						
									
										67
									
								
								gulpfile.js
									
									
									
									
									
								
							@ -55,7 +55,7 @@ var polyfills = [
 | 
				
			|||||||
var files = {
 | 
					var files = {
 | 
				
			||||||
  y: polyfills.concat(["src/**/*.js", "!src/**/*.spec.js"]),
 | 
					  y: polyfills.concat(["src/**/*.js", "!src/**/*.spec.js"]),
 | 
				
			||||||
  lint: ["src/**/*.js", "gulpfile.js"],
 | 
					  lint: ["src/**/*.js", "gulpfile.js"],
 | 
				
			||||||
  test: polyfills.concat(["./node_modules/regenerator/runtime.js", "src/**/*.js"]),
 | 
					  test: polyfills.concat(["src/**/*.js"]),
 | 
				
			||||||
  build_test: ["build_test/y.js"]
 | 
					  build_test: ["build_test/y.js"]
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -68,19 +68,6 @@ var options = minimist(process.argv.slice(2), {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
});
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
gulp.task("build_test", function () {
 | 
					 | 
				
			||||||
  return gulp.src(files.test)
 | 
					 | 
				
			||||||
    .pipe(sourcemaps.init())
 | 
					 | 
				
			||||||
    .pipe(concat(options.name))
 | 
					 | 
				
			||||||
    .pipe(babel({
 | 
					 | 
				
			||||||
      loose: "all",
 | 
					 | 
				
			||||||
      modules: "ignore"
 | 
					 | 
				
			||||||
    }))
 | 
					 | 
				
			||||||
    .pipe(uglify())
 | 
					 | 
				
			||||||
    .pipe(sourcemaps.write())
 | 
					 | 
				
			||||||
    .pipe(gulp.dest("build_test"));
 | 
					 | 
				
			||||||
});
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
gulp.task("build", function () {
 | 
					gulp.task("build", function () {
 | 
				
			||||||
  return gulp.src(files.y)
 | 
					  return gulp.src(files.y)
 | 
				
			||||||
    .pipe(sourcemaps.init())
 | 
					    .pipe(sourcemaps.init())
 | 
				
			||||||
@ -94,14 +81,6 @@ gulp.task("build", function () {
 | 
				
			|||||||
    .pipe(gulp.dest("."));
 | 
					    .pipe(gulp.dest("."));
 | 
				
			||||||
});
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
gulp.task("test", ["build_test"], function () {
 | 
					 | 
				
			||||||
  return gulp.src(files.build_test)
 | 
					 | 
				
			||||||
    .pipe(jasmine({
 | 
					 | 
				
			||||||
      verbose: true,
 | 
					 | 
				
			||||||
      includeStuckTrace: true
 | 
					 | 
				
			||||||
    }));
 | 
					 | 
				
			||||||
});
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
gulp.task("lint", function(){
 | 
					gulp.task("lint", function(){
 | 
				
			||||||
  return gulp.src(files.lint)
 | 
					  return gulp.src(files.lint)
 | 
				
			||||||
    .pipe(eslint())
 | 
					    .pipe(eslint())
 | 
				
			||||||
@ -109,13 +88,47 @@ gulp.task("lint", function(){
 | 
				
			|||||||
    .pipe(eslint.failOnError());
 | 
					    .pipe(eslint.failOnError());
 | 
				
			||||||
});
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
gulp.task("develop", ["test", "build"], function(){
 | 
					gulp.task("test", function () {
 | 
				
			||||||
  gulp.src(files.build_test)
 | 
					  return gulp.src(files.test)
 | 
				
			||||||
    .pipe(watch(files.build_test))
 | 
					    .pipe(sourcemaps.init())
 | 
				
			||||||
 | 
					    .pipe(concat("jasmine"))
 | 
				
			||||||
 | 
					    .pipe(babel({
 | 
				
			||||||
 | 
					      loose: "all",
 | 
				
			||||||
 | 
					      modules: "ignore"
 | 
				
			||||||
 | 
					    }))
 | 
				
			||||||
 | 
					    .pipe(uglify())
 | 
				
			||||||
 | 
					    .pipe(sourcemaps.write())
 | 
				
			||||||
 | 
					    .pipe(gulp.dest("build"))
 | 
				
			||||||
 | 
					    .pipe(jasmine({
 | 
				
			||||||
 | 
					      verbose: true,
 | 
				
			||||||
 | 
					      includeStuckTrace: true
 | 
				
			||||||
 | 
					    }));
 | 
				
			||||||
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					gulp.task("build_jasmine_browser", function(){
 | 
				
			||||||
 | 
					  gulp.src(files.test)
 | 
				
			||||||
 | 
					   .pipe(sourcemaps.init())
 | 
				
			||||||
 | 
					   .pipe(concat("jasmine_browser.js"))
 | 
				
			||||||
 | 
					   .pipe(babel({
 | 
				
			||||||
 | 
					     loose: "all",
 | 
				
			||||||
 | 
					     modules: "ignore",
 | 
				
			||||||
 | 
					     blacklist: ["regenerator"]
 | 
				
			||||||
 | 
					   }))
 | 
				
			||||||
 | 
					   .pipe(sourcemaps.write())
 | 
				
			||||||
 | 
					   .pipe(gulp.dest("build"));
 | 
				
			||||||
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					gulp.task("develop", ["build_jasmine_browser", "test", "build"], function(){
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  gulp.watch(files.test, ["build_jasmine_browser"]);
 | 
				
			||||||
 | 
					  gulp.watch(files.test, ["test"]);
 | 
				
			||||||
 | 
					  gulp.watch(files.test, ["build"]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  return gulp.src("build/jasmine_browser.js")
 | 
				
			||||||
 | 
					    .pipe(watch("build/jasmine_browser.js"))
 | 
				
			||||||
    .pipe(jasmineBrowser.specRunner())
 | 
					    .pipe(jasmineBrowser.specRunner())
 | 
				
			||||||
    .pipe(jasmineBrowser.server({port: options.testport}));
 | 
					    .pipe(jasmineBrowser.server({port: options.testport}));
 | 
				
			||||||
  gulp.watch(files.test, ["build_test", "build"]);
 | 
					
 | 
				
			||||||
  return gulp.watch(files.build_test, ["test"]);
 | 
					 | 
				
			||||||
});
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
gulp.task("default", ["build", "test"]);
 | 
					gulp.task("default", ["build", "test"]);
 | 
				
			||||||
 | 
				
			|||||||
@ -1,76 +0,0 @@
 | 
				
			|||||||
 | 
					 | 
				
			||||||
var IndexedDB = (function(){ //eslint-disable-line no-unused-vars
 | 
					 | 
				
			||||||
  class Transaction {
 | 
					 | 
				
			||||||
    constructor (transaction) {
 | 
					 | 
				
			||||||
      this.transaction = transaction;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    setOperation (op) {
 | 
					 | 
				
			||||||
      return new Promise((resolve, reject)=> {
 | 
					 | 
				
			||||||
        var req = this.transaction.objectStore("OperationBuffer").put(op);
 | 
					 | 
				
			||||||
        req.onsuccess = function () {
 | 
					 | 
				
			||||||
          resolve(op);
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        req.onerror = function () {
 | 
					 | 
				
			||||||
          reject("Could not set Operation!");
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    getOperation (uid) {
 | 
					 | 
				
			||||||
      return new Promise((resolve, reject)=>{
 | 
					 | 
				
			||||||
        var req = this.transaction.objectStore("OperationBuffer").get(uid);
 | 
					 | 
				
			||||||
        req.onsuccess = function () {
 | 
					 | 
				
			||||||
          resolve(req.result);
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        req.onerror = function () {
 | 
					 | 
				
			||||||
          reject("Could not get Operation");
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  class DB {
 | 
					 | 
				
			||||||
    constructor (namespace : string) {
 | 
					 | 
				
			||||||
      this.namespace = namespace;
 | 
					 | 
				
			||||||
      this.ready = new Promise(function(yay, nay){
 | 
					 | 
				
			||||||
        var req = indexedDB.open(namespace); //eslint-disable-line no-undef
 | 
					 | 
				
			||||||
        req.onerror = function(){
 | 
					 | 
				
			||||||
          nay("Couldn't open the IndexedDB database!");
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        req.onsuccess = function(event){
 | 
					 | 
				
			||||||
          yay(event.target.result);
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        req.onupgradeneeded = function(event){
 | 
					 | 
				
			||||||
          var db = event.target.result;
 | 
					 | 
				
			||||||
          db.createObjectStore("OperationBuffer", {keyPath: "uid"});
 | 
					 | 
				
			||||||
          db.createObjectStore("StateVector", {keyPath: "user"});
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
      }).catch(function(message){
 | 
					 | 
				
			||||||
          throw new Error(message);
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    requestTransaction (generator : Function) {
 | 
					 | 
				
			||||||
      this.ready.then(function(){
 | 
					 | 
				
			||||||
        var gen = generator(3);//new Transaction(db.transaction(["OperationBuffer", "StateVector"], "readwrite"))
 | 
					 | 
				
			||||||
        gen.next();
 | 
					 | 
				
			||||||
      });
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  return {
 | 
					 | 
				
			||||||
    "DB": DB,
 | 
					 | 
				
			||||||
    "Transaction": Transaction
 | 
					 | 
				
			||||||
  };
 | 
					 | 
				
			||||||
})();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
function requestTransaction(makeGen : Function){ //eslint-disable-line no-unused-vars
 | 
					 | 
				
			||||||
  var gen = makeGen([1, 2, 3]);
 | 
					 | 
				
			||||||
  function handle(result : Object){
 | 
					 | 
				
			||||||
    if (result.done) {
 | 
					 | 
				
			||||||
      return result.value;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    return result.value.then(function(res){
 | 
					 | 
				
			||||||
      return handle(gen.next(res));
 | 
					 | 
				
			||||||
    }, function(err){
 | 
					 | 
				
			||||||
      return handle(gen.throw(err));
 | 
					 | 
				
			||||||
    });
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  return handle(gen.next());
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
							
								
								
									
										110
									
								
								src/IndexedDB.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										110
									
								
								src/IndexedDB.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,110 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
 | 
					var IndexedDB = (function(){ //eslint-disable-line no-unused-vars
 | 
				
			||||||
 | 
					  var GeneratorFunction = (function*(){}).constructor;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  class Transaction {
 | 
				
			||||||
 | 
					    constructor (transaction) {
 | 
				
			||||||
 | 
					      this.transaction = transaction;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    setOperation (op) {
 | 
				
			||||||
 | 
					      return new Promise((resolve, reject)=> {
 | 
				
			||||||
 | 
					        var req = this.transaction.objectStore("OperationBuffer").put(op);
 | 
				
			||||||
 | 
					        req.onsuccess = function () {
 | 
				
			||||||
 | 
					          resolve(op);
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        req.onerror = function () {
 | 
				
			||||||
 | 
					          reject("Could not set Operation!");
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    getOperation (uid) {
 | 
				
			||||||
 | 
					      return new Promise((resolve, reject)=>{
 | 
				
			||||||
 | 
					        var req = this.transaction.objectStore("OperationBuffer").get(uid);
 | 
				
			||||||
 | 
					        req.onsuccess = function () {
 | 
				
			||||||
 | 
					          resolve(req.result);
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        req.onerror = function () {
 | 
				
			||||||
 | 
					          reject("Could not get Operation");
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    getOperations () {
 | 
				
			||||||
 | 
					      return function* () {
 | 
				
			||||||
 | 
					        var op = yield this.getOperation(["u1", 0]);
 | 
				
			||||||
 | 
					        return op.uid;
 | 
				
			||||||
 | 
					      };
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    /*
 | 
				
			||||||
 | 
					    getOperations: (state_map)->
 | 
				
			||||||
 | 
					      flow = Promise.resolve()
 | 
				
			||||||
 | 
					      ops = []
 | 
				
			||||||
 | 
					      that = this
 | 
				
			||||||
 | 
					      hb = that.t.objectStore("HistoryBuffer")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      that.getStateVector().then (end_state_vector)->
 | 
				
			||||||
 | 
					        for end_state of end_state_vector
 | 
				
			||||||
 | 
					          # convert to the db-structure
 | 
				
			||||||
 | 
					          do (end_state = end_state)->
 | 
				
			||||||
 | 
					            start_state =
 | 
				
			||||||
 | 
					              user: end_state.name
 | 
				
			||||||
 | 
					              state: state_map[end_state] ? 0
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            flow = flow.then ()->
 | 
				
			||||||
 | 
					              from = [start_state.user, start_state.number]
 | 
				
			||||||
 | 
					              to = [end_state.user, end_state.number]
 | 
				
			||||||
 | 
					                cursor = event.target.result
 | 
				
			||||||
 | 
					                if cursor?
 | 
				
			||||||
 | 
					                  ops.push cursor.value # add Operation
 | 
				
			||||||
 | 
					                  cursor.continue()
 | 
				
			||||||
 | 
					                else
 | 
				
			||||||
 | 
					                  # got all ops from this user
 | 
				
			||||||
 | 
					                  defer.resolve ops
 | 
				
			||||||
 | 
					              defer.promise
 | 
				
			||||||
 | 
					    */
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  class DB {
 | 
				
			||||||
 | 
					    constructor (namespace : string) {
 | 
				
			||||||
 | 
					      this.namespace = namespace;
 | 
				
			||||||
 | 
					      this.ready = new Promise(function(yay, nay){
 | 
				
			||||||
 | 
					        var req = indexedDB.open(namespace); //eslint-disable-line no-undef
 | 
				
			||||||
 | 
					        req.onerror = function(){
 | 
				
			||||||
 | 
					          nay("Couldn't open the IndexedDB database!");
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        req.onsuccess = function(event){
 | 
				
			||||||
 | 
					          yay(event.target.result);
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        req.onupgradeneeded = function(event){
 | 
				
			||||||
 | 
					          var db = event.target.result;
 | 
				
			||||||
 | 
					          db.createObjectStore("OperationBuffer", {keyPath: "uid"});
 | 
				
			||||||
 | 
					          db.createObjectStore("StateVector", {keyPath: "user"});
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					      }).catch(function(message){
 | 
				
			||||||
 | 
					          throw new Error(message);
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    requestTransaction (makeGen : Function) {
 | 
				
			||||||
 | 
					      this.ready.then(function(db){
 | 
				
			||||||
 | 
					        var transaction = new Transaction(db.transaction(["OperationBuffer", "StateVector"], "readwrite"));
 | 
				
			||||||
 | 
					        var gen = makeGen.apply(transaction);
 | 
				
			||||||
 | 
					        function handle(result : Object){
 | 
				
			||||||
 | 
					          var v = result.value;
 | 
				
			||||||
 | 
					          if (result.done) {
 | 
				
			||||||
 | 
					            return v;
 | 
				
			||||||
 | 
					          } else if (v.constructor === Promise) {
 | 
				
			||||||
 | 
					            return result.value.then(function(res){
 | 
				
			||||||
 | 
					              return handle(gen.next(res));
 | 
				
			||||||
 | 
					            }, function(err){
 | 
				
			||||||
 | 
					              return handle(gen.throw(err));
 | 
				
			||||||
 | 
					            });
 | 
				
			||||||
 | 
					          } else if (v.constructor === GeneratorFunction){
 | 
				
			||||||
 | 
					            return handle(v.apply(transaction).next());
 | 
				
			||||||
 | 
					          } else {
 | 
				
			||||||
 | 
					            throw new Error("I do only accept Promises and Generators!");
 | 
				
			||||||
 | 
					          }
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					        return handle(gen.next());
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  return DB;
 | 
				
			||||||
 | 
					})();
 | 
				
			||||||
@ -1,24 +1,31 @@
 | 
				
			|||||||
/* @flow */
 | 
					/* @flow */
 | 
				
			||||||
/*eslint-env browser,jasmine,console */
 | 
					/*eslint-env browser,jasmine */
 | 
				
			||||||
 | 
					 | 
				
			||||||
var number = 0;
 | 
					 | 
				
			||||||
function llater(time){
 | 
					 | 
				
			||||||
  return new Promise(function(yay){
 | 
					 | 
				
			||||||
    setTimeout(function(){
 | 
					 | 
				
			||||||
      yay(number++);
 | 
					 | 
				
			||||||
    }, time); //eslint-disable-line no-undef
 | 
					 | 
				
			||||||
  });
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if(typeof window !== "undefined"){
 | 
				
			||||||
  describe("IndexedDB", function() {
 | 
					  describe("IndexedDB", function() {
 | 
				
			||||||
 | 
					    var ob = new IndexedDB("Test");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    it("can create transactions", function(done) {
 | 
					    it("can create transactions", function(done) {
 | 
				
			||||||
    requestTransaction(function*(numbers){
 | 
					      ob.requestTransaction(function*(){
 | 
				
			||||||
      expect(numbers).toEqual([1, 2, 3]);
 | 
					        var op = yield this.setOperation({
 | 
				
			||||||
      expect(yield llater(10)).toEqual(0);
 | 
					          "uid": ["u1", 0],
 | 
				
			||||||
      expect(yield llater(50)).toEqual(1);
 | 
					          "stuff": true
 | 
				
			||||||
 | 
					        });
 | 
				
			||||||
 | 
					        expect(yield this.getOperation(["u1", 0]))
 | 
				
			||||||
 | 
					          .toEqual(op);
 | 
				
			||||||
 | 
					        done();
 | 
				
			||||||
 | 
					      });
 | 
				
			||||||
 | 
					    });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    it("receive remaining operations", function(done){
 | 
				
			||||||
 | 
					      ob.requestTransaction(function*(){
 | 
				
			||||||
 | 
					        expect(yield this.getOperations(["u1", 0]))
 | 
				
			||||||
 | 
					          .toEqual({
 | 
				
			||||||
 | 
					            "uid": ["u1", 0],
 | 
				
			||||||
 | 
					            "stuff": true
 | 
				
			||||||
 | 
					          });
 | 
				
			||||||
        done();
 | 
					        done();
 | 
				
			||||||
      return 10;
 | 
					 | 
				
			||||||
      });
 | 
					      });
 | 
				
			||||||
    });
 | 
					    });
 | 
				
			||||||
  });
 | 
					  });
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user