implemented module loader for yjs
This commit is contained in:
		
							parent
							
								
									138afe39dc
								
							
						
					
					
						commit
						6dc347642b
					
				@ -21,31 +21,10 @@ module.exports = function (gulp, helperOptions) {
 | 
				
			|||||||
    options.regenerator = false
 | 
					    options.regenerator = false
 | 
				
			||||||
    // TODO: include './node_modules/gulp-babel/node_modules/babel-core/node_modules/regenerator/runtime.js'
 | 
					    // TODO: include './node_modules/gulp-babel/node_modules/babel-core/node_modules/regenerator/runtime.js'
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  var concatOrder = [
 | 
					 | 
				
			||||||
    'y.js',
 | 
					 | 
				
			||||||
    'Connector.js',
 | 
					 | 
				
			||||||
    'Database.js',
 | 
					 | 
				
			||||||
    'Transaction.js',
 | 
					 | 
				
			||||||
    'Struct.js',
 | 
					 | 
				
			||||||
    'Utils.js',
 | 
					 | 
				
			||||||
    'Databases/RedBlackTree.js',
 | 
					 | 
				
			||||||
    'Databases/Memory.js',
 | 
					 | 
				
			||||||
    'Databases/IndexedDB.js',
 | 
					 | 
				
			||||||
    'Connectors/Test.js',
 | 
					 | 
				
			||||||
    'Types/Array.js',
 | 
					 | 
				
			||||||
    'Types/Map.js',
 | 
					 | 
				
			||||||
    'Types/TextBind.js'
 | 
					 | 
				
			||||||
  ]
 | 
					 | 
				
			||||||
  var yjsfiles = concatOrder.map(function (f) {
 | 
					 | 
				
			||||||
    return '../yjs/src/' + f
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
  var files = {
 | 
					  var files = {
 | 
				
			||||||
    dist: helperOptions.polyfills.concat(helperOptions.files.map(function (f) {
 | 
					    dist: helperOptions.entry,
 | 
				
			||||||
      return 'src/' + f
 | 
					    specs: helperOptions.specs,
 | 
				
			||||||
    })),
 | 
					    src: './src/**/*.js'
 | 
				
			||||||
    test: ['../yjs/src/Helper.spec.js'].concat(yjsfiles).concat(helperOptions.files.map(function (f) {
 | 
					 | 
				
			||||||
      return 'src/' + f
 | 
					 | 
				
			||||||
    }).concat(['src/' + options.testfiles]))
 | 
					 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  var babelOptions = {
 | 
					  var babelOptions = {
 | 
				
			||||||
@ -54,38 +33,10 @@ module.exports = function (gulp, helperOptions) {
 | 
				
			|||||||
    experimental: true
 | 
					    experimental: true
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  if (options.regenerator) {
 | 
					  if (options.regenerator) {
 | 
				
			||||||
    files.test = helperOptions.polyfills.concat(files.test)
 | 
					    files.specs = helperOptions.polyfills.concat(files.specs)
 | 
				
			||||||
  } else {
 | 
					  } else {
 | 
				
			||||||
    babelOptions.blacklist = 'regenerator'
 | 
					    babelOptions.blacklist = 'regenerator'
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  // babelOptions.blacklist = 'regenerator'
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  gulp.task('dist', ['build:dist'], function () {
 | 
					 | 
				
			||||||
    function createDist (pipe) {
 | 
					 | 
				
			||||||
      return pipe
 | 
					 | 
				
			||||||
        .pipe($.if(options.debug, $.sourcemaps.init({loadMaps: true})))
 | 
					 | 
				
			||||||
        .pipe($.concat(options.targetName))
 | 
					 | 
				
			||||||
        .pipe($.if(!options.debug && options.regenerator, $.uglify()))
 | 
					 | 
				
			||||||
        .pipe($.if(options.debug, $.sourcemaps.write('.')))
 | 
					 | 
				
			||||||
        .pipe(gulp.dest('./dist/'))
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    var pipe
 | 
					 | 
				
			||||||
    if (options.browserify || true) {
 | 
					 | 
				
			||||||
      var browserify = require('browserify')
 | 
					 | 
				
			||||||
      var source = require('vinyl-source-stream')
 | 
					 | 
				
			||||||
      var buffer = require('vinyl-buffer')
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
      pipe = browserify({
 | 
					 | 
				
			||||||
        entries: 'build/' + options.targetName,
 | 
					 | 
				
			||||||
        debug: options.debug
 | 
					 | 
				
			||||||
      }).bundle()
 | 
					 | 
				
			||||||
        .pipe(source(options.targetName))
 | 
					 | 
				
			||||||
        .pipe(buffer())
 | 
					 | 
				
			||||||
    } else {
 | 
					 | 
				
			||||||
      pipe = gulp.src('build/' + options.targetName)
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    return createDist(pipe)
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  gulp.task('dist', function () {
 | 
					  gulp.task('dist', function () {
 | 
				
			||||||
    var browserify = require('browserify')
 | 
					    var browserify = require('browserify')
 | 
				
			||||||
@ -99,7 +50,7 @@ module.exports = function (gulp, helperOptions) {
 | 
				
			|||||||
      .pipe(source(options.targetName))
 | 
					      .pipe(source(options.targetName))
 | 
				
			||||||
      .pipe(buffer())
 | 
					      .pipe(buffer())
 | 
				
			||||||
      .pipe($.if(options.debug, $.sourcemaps.init({loadMaps: true})))
 | 
					      .pipe($.if(options.debug, $.sourcemaps.init({loadMaps: true})))
 | 
				
			||||||
      .pipe($.concat(options.targetName))
 | 
					      .pipe($.if(!options.debug && options.regenerator, $.babel(babelOptions)))
 | 
				
			||||||
      .pipe($.if(!options.debug && options.regenerator, $.uglify()))
 | 
					      .pipe($.if(!options.debug && options.regenerator, $.uglify()))
 | 
				
			||||||
      .pipe($.if(options.debug, $.sourcemaps.write('.')))
 | 
					      .pipe($.if(options.debug, $.sourcemaps.write('.')))
 | 
				
			||||||
      .pipe(gulp.dest('./dist/'))
 | 
					      .pipe(gulp.dest('./dist/'))
 | 
				
			||||||
@ -108,11 +59,46 @@ module.exports = function (gulp, helperOptions) {
 | 
				
			|||||||
  gulp.task('watch:dist', function (cb) {
 | 
					  gulp.task('watch:dist', function (cb) {
 | 
				
			||||||
    options.debug = true
 | 
					    options.debug = true
 | 
				
			||||||
    runSequence('dist', function () {
 | 
					    runSequence('dist', function () {
 | 
				
			||||||
      gulp.watch(files.dist, ['dist'])
 | 
					      gulp.watch(files.src, ['dist'])
 | 
				
			||||||
      cb()
 | 
					      cb()
 | 
				
			||||||
    })
 | 
					    })
 | 
				
			||||||
  })
 | 
					  })
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  gulp.task('dev:node', ['test'], function () {
 | 
				
			||||||
 | 
					    gulp.watch(files.src, ['test'])
 | 
				
			||||||
 | 
					  })
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  gulp.task('spec-build', function () {
 | 
				
			||||||
 | 
					    var browserify = require('browserify')
 | 
				
			||||||
 | 
					    var source = require('vinyl-source-stream')
 | 
				
			||||||
 | 
					    var buffer = require('vinyl-buffer')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return browserify({
 | 
				
			||||||
 | 
					      entries: files.specs,
 | 
				
			||||||
 | 
					      debug: options.debug
 | 
				
			||||||
 | 
					    }).bundle()
 | 
				
			||||||
 | 
					      .pipe(source('specs.js'))
 | 
				
			||||||
 | 
					      .pipe(buffer())
 | 
				
			||||||
 | 
					      .pipe($.sourcemaps.init({loadMaps: true}))
 | 
				
			||||||
 | 
					      .pipe($.sourcemaps.write())
 | 
				
			||||||
 | 
					      .pipe(gulp.dest('./build/'))
 | 
				
			||||||
 | 
					  })
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  gulp.task('dev:browser', ['spec-build'], function () {
 | 
				
			||||||
 | 
					    gulp.watch(files.src, ['spec-build'])
 | 
				
			||||||
 | 
					    return gulp.src('./build/specs.js')
 | 
				
			||||||
 | 
					      .pipe($.jasmineBrowser.specRunner())
 | 
				
			||||||
 | 
					      .pipe($.jasmineBrowser.server({port: options.testport}))
 | 
				
			||||||
 | 
					  })
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  gulp.task('test', function () {
 | 
				
			||||||
 | 
					    return gulp.src(files.specs)
 | 
				
			||||||
 | 
					      .pipe($.jasmine({
 | 
				
			||||||
 | 
					        verbose: true,
 | 
				
			||||||
 | 
					        includeStuckTrace: true
 | 
				
			||||||
 | 
					      }))
 | 
				
			||||||
 | 
					  })
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  gulp.task('updateSubmodule', function () {
 | 
					  gulp.task('updateSubmodule', function () {
 | 
				
			||||||
    return gulp.src('./package.json', {read: false})
 | 
					    return gulp.src('./package.json', {read: false})
 | 
				
			||||||
      .pipe($.shell([
 | 
					      .pipe($.shell([
 | 
				
			||||||
@ -168,24 +154,4 @@ module.exports = function (gulp, helperOptions) {
 | 
				
			|||||||
        }))
 | 
					        }))
 | 
				
			||||||
    })
 | 
					    })
 | 
				
			||||||
  })
 | 
					  })
 | 
				
			||||||
 | 
					 | 
				
			||||||
  gulp.task('dev:node', ['test'], function () {
 | 
					 | 
				
			||||||
    gulp.watch(files.dist, ['test'])
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  gulp.task('dev:browser', ['watch:build'], function () {
 | 
					 | 
				
			||||||
    return gulp.src(files.test)
 | 
					 | 
				
			||||||
      .pipe($.watch(['build/**/*']))
 | 
					 | 
				
			||||||
      .pipe($.jasmineBrowser.specRunner())
 | 
					 | 
				
			||||||
      .pipe($.jasmineBrowser.server({port: options.testport}))
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  gulp.task('test', function () {
 | 
					 | 
				
			||||||
    console.log(files.test)
 | 
					 | 
				
			||||||
    return gulp.src('./dist/y.js')
 | 
					 | 
				
			||||||
      .pipe($.jasmine({
 | 
					 | 
				
			||||||
        verbose: true,
 | 
					 | 
				
			||||||
        includeStuckTrace: true
 | 
					 | 
				
			||||||
      }))
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										24
									
								
								gulpfile.js
									
									
									
									
									
								
							
							
						
						
									
										24
									
								
								gulpfile.js
									
									
									
									
									
								
							@ -49,23 +49,15 @@ var runSequence = require('run-sequence').use(gulp)
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
require('./gulpfile.helper.js')(gulp, {
 | 
					require('./gulpfile.helper.js')(gulp, {
 | 
				
			||||||
  polyfills: [],
 | 
					  polyfills: [],
 | 
				
			||||||
  files: [
 | 
					  entry: './src/y.js',
 | 
				
			||||||
    'y.js',
 | 
					 | 
				
			||||||
    'Connector.js',
 | 
					 | 
				
			||||||
    'Database.js',
 | 
					 | 
				
			||||||
    'Transaction.js',
 | 
					 | 
				
			||||||
    'Struct.js',
 | 
					 | 
				
			||||||
    'Utils.js',
 | 
					 | 
				
			||||||
    'Databases/RedBlackTree.js',
 | 
					 | 
				
			||||||
    'Databases/Memory.js',
 | 
					 | 
				
			||||||
    'Databases/IndexedDB.js',
 | 
					 | 
				
			||||||
    'Connectors/Test.js',
 | 
					 | 
				
			||||||
    'Types/Array.js',
 | 
					 | 
				
			||||||
    'Types/Map.js',
 | 
					 | 
				
			||||||
    'Types/TextBind.js'
 | 
					 | 
				
			||||||
  ],
 | 
					 | 
				
			||||||
  targetName: 'y.js',
 | 
					  targetName: 'y.js',
 | 
				
			||||||
  moduleName: 'yjs'
 | 
					  moduleName: 'yjs',
 | 
				
			||||||
 | 
					  specs: [
 | 
				
			||||||
 | 
					    './src/Databases/RedBlackTree.spec.js',
 | 
				
			||||||
 | 
					    './src/Types/Array.spec.js',
 | 
				
			||||||
 | 
					    './src/Types/Map.spec.js',
 | 
				
			||||||
 | 
					    './src/Database.spec.js'
 | 
				
			||||||
 | 
					  ]
 | 
				
			||||||
})
 | 
					})
 | 
				
			||||||
 | 
					
 | 
				
			||||||
gulp.task('dev:examples', ['updateSubmodule', 'watch:dist'], function () {
 | 
					gulp.task('dev:examples', ['updateSubmodule', 'watch:dist'], function () {
 | 
				
			||||||
 | 
				
			|||||||
@ -68,6 +68,7 @@
 | 
				
			|||||||
    "run-sequence": "^1.1.4",
 | 
					    "run-sequence": "^1.1.4",
 | 
				
			||||||
    "standard": "^5.2.2",
 | 
					    "standard": "^5.2.2",
 | 
				
			||||||
    "vinyl-buffer": "^1.0.0",
 | 
					    "vinyl-buffer": "^1.0.0",
 | 
				
			||||||
    "vinyl-source-stream": "^1.1.0"
 | 
					    "vinyl-source-stream": "^1.1.0",
 | 
				
			||||||
 | 
					    "watchify": "^3.6.0"
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,6 +1,6 @@
 | 
				
			|||||||
/* globals Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class AbstractConnector {
 | 
					  class AbstractConnector {
 | 
				
			||||||
    /*
 | 
					    /*
 | 
				
			||||||
      opts contains the following information:
 | 
					      opts contains the following information:
 | 
				
			||||||
@ -326,3 +326,4 @@ class AbstractConnector {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  Y.AbstractConnector = AbstractConnector
 | 
					  Y.AbstractConnector = AbstractConnector
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,6 +1,7 @@
 | 
				
			|||||||
/* global getRandom, Y, wait, async */
 | 
					/* global getRandom, wait, async */
 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  var globalRoom = {
 | 
					  var globalRoom = {
 | 
				
			||||||
    users: {},
 | 
					    users: {},
 | 
				
			||||||
    buffers: {},
 | 
					    buffers: {},
 | 
				
			||||||
@ -134,3 +135,4 @@ class Test extends Y.AbstractConnector {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  Y.Test = Test
 | 
					  Y.Test = Test
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,6 +1,6 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  /*
 | 
					  /*
 | 
				
			||||||
    Partial definition of an OperationStore.
 | 
					    Partial definition of an OperationStore.
 | 
				
			||||||
    TODO: name it Database, operation store only holds operations.
 | 
					    TODO: name it Database, operation store only holds operations.
 | 
				
			||||||
@ -339,3 +339,4 @@ class AbstractDatabase {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  Y.AbstractDatabase = AbstractDatabase
 | 
					  Y.AbstractDatabase = AbstractDatabase
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,5 +1,8 @@
 | 
				
			|||||||
/* global Y, async, databases */
 | 
					/* global async, databases */
 | 
				
			||||||
/* eslint-env browser,jasmine,console */
 | 
					/* eslint-env browser,jasmine,console */
 | 
				
			||||||
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var Y = require('./SpecHelper.js')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
for (let database of databases) {
 | 
					for (let database of databases) {
 | 
				
			||||||
  describe(`Database (${database})`, function () {
 | 
					  describe(`Database (${database})`, function () {
 | 
				
			||||||
 | 
				
			|||||||
@ -1,8 +1,6 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
Y.IndexedDB = (function () {
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class Store {
 | 
					  class Store {
 | 
				
			||||||
    constructor (transaction, name) {
 | 
					    constructor (transaction, name) {
 | 
				
			||||||
      this.store = transaction.objectStore(name)
 | 
					      this.store = transaction.objectStore(name)
 | 
				
			||||||
@ -177,5 +175,5 @@ Y.IndexedDB = (function () {
 | 
				
			|||||||
      yield window.indexedDB.deleteDatabase(this.namespace)
 | 
					      yield window.indexedDB.deleteDatabase(this.namespace)
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  return OperationStore
 | 
					  Y.IndexedDB = OperationStore
 | 
				
			||||||
})()
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,19 +0,0 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
/* eslint-env browser,jasmine */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
if (typeof window !== 'undefined' && false) {
 | 
					 | 
				
			||||||
  describe('IndexedDB', function () {
 | 
					 | 
				
			||||||
    var ob
 | 
					 | 
				
			||||||
    beforeAll(function () {
 | 
					 | 
				
			||||||
      ob = new Y.IndexedDB(null, {namespace: 'Test', gcTimeout: -1})
 | 
					 | 
				
			||||||
    })
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    afterAll(function (done) {
 | 
					 | 
				
			||||||
      ob.requestTransaction(function *() {
 | 
					 | 
				
			||||||
        yield* ob.removeDatabase()
 | 
					 | 
				
			||||||
        ob = null
 | 
					 | 
				
			||||||
        done()
 | 
					 | 
				
			||||||
      })
 | 
					 | 
				
			||||||
    })
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
@ -1,7 +1,6 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
Y.Memory = (function () {
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class Transaction extends Y.Transaction {
 | 
					  class Transaction extends Y.Transaction {
 | 
				
			||||||
    constructor (store) {
 | 
					    constructor (store) {
 | 
				
			||||||
      super(store)
 | 
					      super(store)
 | 
				
			||||||
@ -59,5 +58,5 @@ Y.Memory = (function () {
 | 
				
			|||||||
      delete this.ds
 | 
					      delete this.ds
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  return Database
 | 
					  Y.Memory = Database
 | 
				
			||||||
})()
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,10 +1,10 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					/*
 | 
				
			||||||
  This file contains a not so fancy implemantion of a Red Black Tree.
 | 
					  This file contains a not so fancy implemantion of a Red Black Tree.
 | 
				
			||||||
*/
 | 
					*/
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class N {
 | 
					  class N {
 | 
				
			||||||
    // A created node is always red!
 | 
					    // A created node is always red!
 | 
				
			||||||
    constructor (val) {
 | 
					    constructor (val) {
 | 
				
			||||||
@ -487,3 +487,4 @@ class RBTree {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  Y.utils.RBTree = RBTree
 | 
					  Y.utils.RBTree = RBTree
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,6 +1,7 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
/* eslint-env browser,jasmine,console */
 | 
					/* eslint-env browser,jasmine,console */
 | 
				
			||||||
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var Y = require('../SpecHelper.js')
 | 
				
			||||||
var numberOfRBTreeTests = 1000
 | 
					var numberOfRBTreeTests = 1000
 | 
				
			||||||
 | 
					
 | 
				
			||||||
function itRedNodesDoNotHaveBlackChildren () {
 | 
					function itRedNodesDoNotHaveBlackChildren () {
 | 
				
			||||||
 | 
				
			|||||||
@ -1,288 +0,0 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
/* eslint-env browser, jasmine */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/*
 | 
					 | 
				
			||||||
  This is just a compilation of functions that help to test this library!
 | 
					 | 
				
			||||||
*/
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// When testing, you store everything on the global object. We call it g
 | 
					 | 
				
			||||||
var g
 | 
					 | 
				
			||||||
if (typeof global !== 'undefined') {
 | 
					 | 
				
			||||||
  g = global
 | 
					 | 
				
			||||||
} else if (typeof window !== 'undefined') {
 | 
					 | 
				
			||||||
  g = window
 | 
					 | 
				
			||||||
} else {
 | 
					 | 
				
			||||||
  throw new Error('No global object?')
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
g.g = g
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.YConcurrency_TestingMode = true
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
jasmine.DEFAULT_TIMEOUT_INTERVAL = 20000
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.describeManyTimes = function describeManyTimes (times, name, f) {
 | 
					 | 
				
			||||||
  for (var i = 0; i < times; i++) {
 | 
					 | 
				
			||||||
    describe(name, f)
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/*
 | 
					 | 
				
			||||||
  Wait for a specified amount of time (in ms). defaults to 5ms
 | 
					 | 
				
			||||||
*/
 | 
					 | 
				
			||||||
function wait (t) {
 | 
					 | 
				
			||||||
  if (t == null) {
 | 
					 | 
				
			||||||
    t = 5
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  return new Promise(function (resolve) {
 | 
					 | 
				
			||||||
    setTimeout(function () {
 | 
					 | 
				
			||||||
      resolve()
 | 
					 | 
				
			||||||
    }, t * 2)
 | 
					 | 
				
			||||||
  })
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
g.wait = wait
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.databases = ['Memory']
 | 
					 | 
				
			||||||
if (typeof window !== 'undefined') {
 | 
					 | 
				
			||||||
  g.databases.push('IndexedDB')
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/*
 | 
					 | 
				
			||||||
  returns a random element of o.
 | 
					 | 
				
			||||||
  works on Object, and Array
 | 
					 | 
				
			||||||
*/
 | 
					 | 
				
			||||||
function getRandom (o) {
 | 
					 | 
				
			||||||
  if (o instanceof Array) {
 | 
					 | 
				
			||||||
    return o[Math.floor(Math.random() * o.length)]
 | 
					 | 
				
			||||||
  } else if (o.constructor === Object) {
 | 
					 | 
				
			||||||
    var ks = []
 | 
					 | 
				
			||||||
    for (var key in o) {
 | 
					 | 
				
			||||||
      ks.push(key)
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    return o[getRandom(ks)]
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
g.getRandom = getRandom
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
function getRandomNumber (n) {
 | 
					 | 
				
			||||||
  if (n == null) {
 | 
					 | 
				
			||||||
    n = 9999
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  return Math.floor(Math.random() * n)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
g.getRandomNumber = getRandomNumber
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
function * applyTransactions (relAmount, numberOfTransactions, objects, users, transactions) {
 | 
					 | 
				
			||||||
  function randomTransaction (root) {
 | 
					 | 
				
			||||||
    var f = getRandom(transactions)
 | 
					 | 
				
			||||||
    f(root)
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  for (var i = 0; i < numberOfTransactions * relAmount + 1; i++) {
 | 
					 | 
				
			||||||
    var r = Math.random()
 | 
					 | 
				
			||||||
    if (r >= 0.5) {
 | 
					 | 
				
			||||||
      // 50% chance to flush
 | 
					 | 
				
			||||||
      users[0].connector.flushOne() // flushes for some user.. (not necessarily 0)
 | 
					 | 
				
			||||||
    } else if (r >= 0.05) {
 | 
					 | 
				
			||||||
      // 45% chance to create operation
 | 
					 | 
				
			||||||
      randomTransaction(getRandom(objects))
 | 
					 | 
				
			||||||
    } else {
 | 
					 | 
				
			||||||
      // 5% chance to disconnect/reconnect
 | 
					 | 
				
			||||||
      var u = getRandom(users)
 | 
					 | 
				
			||||||
      if (u.connector.isDisconnected()) {
 | 
					 | 
				
			||||||
        yield u.reconnect()
 | 
					 | 
				
			||||||
      } else {
 | 
					 | 
				
			||||||
        yield u.disconnect()
 | 
					 | 
				
			||||||
      }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    yield wait()
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.applyRandomTransactionsAllRejoinNoGC = async(function * applyRandomTransactions (users, objects, transactions, numberOfTransactions) {
 | 
					 | 
				
			||||||
  yield* applyTransactions(1, numberOfTransactions, objects, users, transactions)
 | 
					 | 
				
			||||||
  yield users[0].connector.flushAll()
 | 
					 | 
				
			||||||
  yield wait()
 | 
					 | 
				
			||||||
  for (var u in users) {
 | 
					 | 
				
			||||||
    yield users[u].reconnect()
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  yield wait(100)
 | 
					 | 
				
			||||||
  yield users[0].connector.flushAll()
 | 
					 | 
				
			||||||
  yield g.garbageCollectAllUsers(users)
 | 
					 | 
				
			||||||
})
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.applyRandomTransactionsWithGC = async(function * applyRandomTransactions (users, objects, transactions, numberOfTransactions) {
 | 
					 | 
				
			||||||
  yield* applyTransactions(1, numberOfTransactions, objects, users.slice(1), transactions)
 | 
					 | 
				
			||||||
  yield users[0].connector.flushAll()
 | 
					 | 
				
			||||||
  yield g.garbageCollectAllUsers(users)
 | 
					 | 
				
			||||||
  yield wait(100)
 | 
					 | 
				
			||||||
  for (var u in users) {
 | 
					 | 
				
			||||||
    // TODO: here, we enforce that two users never sync at the same time with u[0]
 | 
					 | 
				
			||||||
    //       enforce that in the connector itself!
 | 
					 | 
				
			||||||
    yield users[u].reconnect()
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  yield wait(100)
 | 
					 | 
				
			||||||
  yield users[0].connector.flushAll()
 | 
					 | 
				
			||||||
  yield wait(100)
 | 
					 | 
				
			||||||
  yield g.garbageCollectAllUsers(users)
 | 
					 | 
				
			||||||
})
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.garbageCollectAllUsers = async(function * garbageCollectAllUsers (users) {
 | 
					 | 
				
			||||||
  // gc two times because of the two gc phases (really collect everything)
 | 
					 | 
				
			||||||
  yield wait(100)
 | 
					 | 
				
			||||||
  for (var i in users) {
 | 
					 | 
				
			||||||
    yield users[i].db.garbageCollect()
 | 
					 | 
				
			||||||
    yield users[i].db.garbageCollect()
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  yield wait(100)
 | 
					 | 
				
			||||||
})
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.compareAllUsers = async(function * compareAllUsers (users) {
 | 
					 | 
				
			||||||
  var s1, s2 // state sets
 | 
					 | 
				
			||||||
  var ds1, ds2 // delete sets
 | 
					 | 
				
			||||||
  var allDels1, allDels2 // all deletions
 | 
					 | 
				
			||||||
  var db1 = [] // operation store of user1
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  // t1 and t2 basically do the same. They define t[1,2], ds[1,2], and allDels[1,2]
 | 
					 | 
				
			||||||
  function * t1 () {
 | 
					 | 
				
			||||||
    s1 = yield* this.getStateSet()
 | 
					 | 
				
			||||||
    ds1 = yield* this.getDeleteSet()
 | 
					 | 
				
			||||||
    allDels1 = []
 | 
					 | 
				
			||||||
    yield* this.ds.iterate(this, null, null, function * (d) {
 | 
					 | 
				
			||||||
      allDels1.push(d)
 | 
					 | 
				
			||||||
    })
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  function * t2 () {
 | 
					 | 
				
			||||||
    s2 = yield* this.getStateSet()
 | 
					 | 
				
			||||||
    ds2 = yield* this.getDeleteSet()
 | 
					 | 
				
			||||||
    allDels2 = []
 | 
					 | 
				
			||||||
    yield* this.ds.iterate(this, null, null, function * (d) {
 | 
					 | 
				
			||||||
      allDels2.push(d)
 | 
					 | 
				
			||||||
    })
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  yield users[0].connector.flushAll()
 | 
					 | 
				
			||||||
  yield wait()
 | 
					 | 
				
			||||||
  yield g.garbageCollectAllUsers(users)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  for (var uid = 0; uid < users.length; uid++) {
 | 
					 | 
				
			||||||
    var u = users[uid]
 | 
					 | 
				
			||||||
    u.db.requestTransaction(function * () {
 | 
					 | 
				
			||||||
      // compare deleted ops against deleteStore
 | 
					 | 
				
			||||||
      yield* this.os.iterate(this, null, null, function * (o) {
 | 
					 | 
				
			||||||
        if (o.deleted === true) {
 | 
					 | 
				
			||||||
          expect(yield* this.isDeleted(o.id)).toBeTruthy()
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
      })
 | 
					 | 
				
			||||||
      // compare deleteStore against deleted ops
 | 
					 | 
				
			||||||
      var ds = []
 | 
					 | 
				
			||||||
      yield* this.ds.iterate(this, null, null, function * (d) {
 | 
					 | 
				
			||||||
        ds.push(d)
 | 
					 | 
				
			||||||
      })
 | 
					 | 
				
			||||||
      for (var j in ds) {
 | 
					 | 
				
			||||||
        var d = ds[j]
 | 
					 | 
				
			||||||
        for (var i = 0; i < d.len; i++) {
 | 
					 | 
				
			||||||
          var o = yield* this.getOperation([d.id[0], d.id[1] + i])
 | 
					 | 
				
			||||||
          // gc'd or deleted
 | 
					 | 
				
			||||||
          if (d.gc) {
 | 
					 | 
				
			||||||
            expect(o).toBeFalsy()
 | 
					 | 
				
			||||||
          } else {
 | 
					 | 
				
			||||||
            expect(o.deleted).toBeTruthy()
 | 
					 | 
				
			||||||
          }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
      }
 | 
					 | 
				
			||||||
    })
 | 
					 | 
				
			||||||
    // compare allDels tree
 | 
					 | 
				
			||||||
    yield wait()
 | 
					 | 
				
			||||||
    if (s1 == null) {
 | 
					 | 
				
			||||||
      u.db.requestTransaction(function * () {
 | 
					 | 
				
			||||||
        yield* t1.call(this)
 | 
					 | 
				
			||||||
        yield* this.os.iterate(this, null, null, function * (o) {
 | 
					 | 
				
			||||||
          o = Y.utils.copyObject(o)
 | 
					 | 
				
			||||||
          delete o.origin
 | 
					 | 
				
			||||||
          db1.push(o)
 | 
					 | 
				
			||||||
        })
 | 
					 | 
				
			||||||
      })
 | 
					 | 
				
			||||||
      yield wait()
 | 
					 | 
				
			||||||
    } else {
 | 
					 | 
				
			||||||
      // TODO: make requestTransaction return a promise..
 | 
					 | 
				
			||||||
      u.db.requestTransaction(function * () {
 | 
					 | 
				
			||||||
        yield* t2.call(this)
 | 
					 | 
				
			||||||
        expect(s1).toEqual(s2)
 | 
					 | 
				
			||||||
        expect(allDels1).toEqual(allDels2) // inner structure
 | 
					 | 
				
			||||||
        expect(ds1).toEqual(ds2) // exported structure
 | 
					 | 
				
			||||||
        var count = 0
 | 
					 | 
				
			||||||
        yield* this.os.iterate(this, null, null, function * (o) {
 | 
					 | 
				
			||||||
          o = Y.utils.copyObject(o)
 | 
					 | 
				
			||||||
          delete o.origin
 | 
					 | 
				
			||||||
          expect(db1[count++]).toEqual(o)
 | 
					 | 
				
			||||||
        })
 | 
					 | 
				
			||||||
      })
 | 
					 | 
				
			||||||
      yield wait()
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
})
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.createUsers = async(function * createUsers (self, numberOfUsers, database) {
 | 
					 | 
				
			||||||
  if (Y.utils.globalRoom.users[0] != null) {
 | 
					 | 
				
			||||||
    yield Y.utils.globalRoom.users[0].flushAll()
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  // destroy old users
 | 
					 | 
				
			||||||
  for (var u in Y.utils.globalRoom.users) {
 | 
					 | 
				
			||||||
    Y.utils.globalRoom.users[u].y.destroy()
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  self.users = null
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  var promises = []
 | 
					 | 
				
			||||||
  for (var i = 0; i < numberOfUsers; i++) {
 | 
					 | 
				
			||||||
    promises.push(Y({
 | 
					 | 
				
			||||||
      db: {
 | 
					 | 
				
			||||||
        name: database,
 | 
					 | 
				
			||||||
        namespace: 'User ' + i,
 | 
					 | 
				
			||||||
        cleanStart: true,
 | 
					 | 
				
			||||||
        gcTimeout: -1
 | 
					 | 
				
			||||||
      },
 | 
					 | 
				
			||||||
      connector: {
 | 
					 | 
				
			||||||
        name: 'Test',
 | 
					 | 
				
			||||||
        debug: false
 | 
					 | 
				
			||||||
      }
 | 
					 | 
				
			||||||
    }))
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  self.users = yield Promise.all(promises)
 | 
					 | 
				
			||||||
  return self.users
 | 
					 | 
				
			||||||
})
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/*
 | 
					 | 
				
			||||||
  Until async/await arrives in js, we use this function to wait for promises
 | 
					 | 
				
			||||||
  by yielding them.
 | 
					 | 
				
			||||||
*/
 | 
					 | 
				
			||||||
function async (makeGenerator) {
 | 
					 | 
				
			||||||
  return function (arg) {
 | 
					 | 
				
			||||||
    var generator = makeGenerator.apply(this, arguments)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    function handle (result) {
 | 
					 | 
				
			||||||
      if (result.done) return Promise.resolve(result.value)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
      return Promise.resolve(result.value).then(function (res) {
 | 
					 | 
				
			||||||
        return handle(generator.next(res))
 | 
					 | 
				
			||||||
      }, function (err) {
 | 
					 | 
				
			||||||
        return handle(generator.throw(err))
 | 
					 | 
				
			||||||
      })
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    try {
 | 
					 | 
				
			||||||
      return handle(generator.next())
 | 
					 | 
				
			||||||
    } catch (ex) {
 | 
					 | 
				
			||||||
      generator.throw(ex)
 | 
					 | 
				
			||||||
      // return Promise.reject(ex)
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
g.async = async
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
function logUsers (self) {
 | 
					 | 
				
			||||||
  if (self.constructor === Array) {
 | 
					 | 
				
			||||||
    self = {users: self}
 | 
					 | 
				
			||||||
  }
 | 
					 | 
				
			||||||
  self.users[0].db.logTable()
 | 
					 | 
				
			||||||
  self.users[1].db.logTable()
 | 
					 | 
				
			||||||
  self.users[2].db.logTable()
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
g.logUsers = logUsers
 | 
					 | 
				
			||||||
@ -1,4 +1,3 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					/*
 | 
				
			||||||
@ -19,7 +18,7 @@
 | 
				
			|||||||
 * requiredOps
 | 
					 * requiredOps
 | 
				
			||||||
     - Operations that are required to execute this operation.
 | 
					     - Operations that are required to execute this operation.
 | 
				
			||||||
*/
 | 
					*/
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  var Struct = {
 | 
					  var Struct = {
 | 
				
			||||||
    /* This is the only operation that is actually not a structure, because
 | 
					    /* This is the only operation that is actually not a structure, because
 | 
				
			||||||
    it is not stored in the OS. This is why it _does not_ have an id
 | 
					    it is not stored in the OS. This is why it _does not_ have an id
 | 
				
			||||||
@ -334,3 +333,4 @@ var Struct = {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  Y.Struct = Struct
 | 
					  Y.Struct = Struct
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,4 +1,3 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					/*
 | 
				
			||||||
@ -74,6 +73,7 @@
 | 
				
			|||||||
     - this is called only by `getOperations(startSS)`. It makes an operation
 | 
					     - this is called only by `getOperations(startSS)`. It makes an operation
 | 
				
			||||||
       applyable on a given SS.
 | 
					       applyable on a given SS.
 | 
				
			||||||
*/
 | 
					*/
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class Transaction {
 | 
					  class Transaction {
 | 
				
			||||||
    /*
 | 
					    /*
 | 
				
			||||||
      Get a type based on the id of its model.
 | 
					      Get a type based on the id of its model.
 | 
				
			||||||
@ -651,3 +651,4 @@ class Transaction {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  Y.Transaction = Transaction
 | 
					  Y.Transaction = Transaction
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,7 +1,6 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
;(function () {
 | 
					function extend (Y) {
 | 
				
			||||||
  class YArray {
 | 
					  class YArray {
 | 
				
			||||||
    constructor (os, _model, idArray, valArray) {
 | 
					    constructor (os, _model, idArray, valArray) {
 | 
				
			||||||
      this.os = os
 | 
					      this.os = os
 | 
				
			||||||
@ -166,7 +165,7 @@
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  Y.Array = new Y.utils.CustomType({
 | 
					  Y.extend('Array', new Y.utils.CustomType({
 | 
				
			||||||
    class: YArray,
 | 
					    class: YArray,
 | 
				
			||||||
    createType: function * YArrayCreator () {
 | 
					    createType: function * YArrayCreator () {
 | 
				
			||||||
      var modelid = this.store.getNextOpId()
 | 
					      var modelid = this.store.getNextOpId()
 | 
				
			||||||
@ -188,5 +187,11 @@
 | 
				
			|||||||
      })
 | 
					      })
 | 
				
			||||||
      return new YArray(os, model.id, idArray, valArray)
 | 
					      return new YArray(os, model.id, idArray, valArray)
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  })
 | 
					  }))
 | 
				
			||||||
})()
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if (typeof Y !== 'undefined') {
 | 
				
			||||||
 | 
					  extend(Y)
 | 
				
			||||||
 | 
					} else {
 | 
				
			||||||
 | 
					  module.exports = extend
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,6 +1,8 @@
 | 
				
			|||||||
/* global createUsers, databases, wait, Y, compareAllUsers, getRandomNumber, applyRandomTransactionsAllRejoinNoGC, applyRandomTransactionsWithGC, async, garbageCollectAllUsers, describeManyTimes */
 | 
					/* global createUsers, databases, wait, compareAllUsers, getRandomNumber, applyRandomTransactionsAllRejoinNoGC, applyRandomTransactionsWithGC, async, garbageCollectAllUsers, describeManyTimes */
 | 
				
			||||||
/* eslint-env browser,jasmine */
 | 
					/* eslint-env browser,jasmine */
 | 
				
			||||||
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var Y = require('../SpecHelper.js')
 | 
				
			||||||
var numberOfYArrayTests = 10
 | 
					var numberOfYArrayTests = 10
 | 
				
			||||||
var repeatArrayTests = 2
 | 
					var repeatArrayTests = 2
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
@ -1,7 +1,6 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
;(function () {
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class YMap {
 | 
					  class YMap {
 | 
				
			||||||
    constructor (os, model, contents, opContents) {
 | 
					    constructor (os, model, contents, opContents) {
 | 
				
			||||||
      this._model = model.id
 | 
					      this._model = model.id
 | 
				
			||||||
@ -292,4 +291,4 @@
 | 
				
			|||||||
      return new YMap(os, model, contents, opContents)
 | 
					      return new YMap(os, model, contents, opContents)
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  })
 | 
					  })
 | 
				
			||||||
})()
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,6 +1,8 @@
 | 
				
			|||||||
/* global createUsers, Y, databases, compareAllUsers, getRandomNumber, applyRandomTransactionsAllRejoinNoGC, applyRandomTransactionsWithGC, async, describeManyTimes */
 | 
					/* global createUsers, databases, compareAllUsers, getRandomNumber, applyRandomTransactionsAllRejoinNoGC, applyRandomTransactionsWithGC, async, describeManyTimes */
 | 
				
			||||||
/* eslint-env browser,jasmine */
 | 
					/* eslint-env browser,jasmine */
 | 
				
			||||||
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var Y = require('../SpecHelper.js')
 | 
				
			||||||
var numberOfYMapTests = 10
 | 
					var numberOfYMapTests = 10
 | 
				
			||||||
var repeatMapTeasts = 1
 | 
					var repeatMapTeasts = 1
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
@ -1,7 +1,6 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
;(function () {
 | 
					module.exports = function (Y) {
 | 
				
			||||||
  class YTextBind extends Y.Array['class'] {
 | 
					  class YTextBind extends Y.Array['class'] {
 | 
				
			||||||
    constructor (os, _model, idArray, valArray) {
 | 
					    constructor (os, _model, idArray, valArray) {
 | 
				
			||||||
      super(os, _model, idArray, valArray)
 | 
					      super(os, _model, idArray, valArray)
 | 
				
			||||||
@ -287,4 +286,4 @@
 | 
				
			|||||||
      return new YTextBind(os, model.id, idArray, valArray)
 | 
					      return new YTextBind(os, model.id, idArray, valArray)
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  })
 | 
					  })
 | 
				
			||||||
})()
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -1,4 +1,3 @@
 | 
				
			|||||||
/* global Y */
 | 
					 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					/*
 | 
				
			||||||
@ -21,6 +20,9 @@
 | 
				
			|||||||
  database request to finish). EventHandler will help you to make your type
 | 
					  database request to finish). EventHandler will help you to make your type
 | 
				
			||||||
  synchronously.
 | 
					  synchronously.
 | 
				
			||||||
*/
 | 
					*/
 | 
				
			||||||
 | 
					module.exports = function (Y) {
 | 
				
			||||||
 | 
					  Y.utils = {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  class EventHandler {
 | 
					  class EventHandler {
 | 
				
			||||||
    /*
 | 
					    /*
 | 
				
			||||||
      onevent: is called when the structure changes.
 | 
					      onevent: is called when the structure changes.
 | 
				
			||||||
@ -196,3 +198,4 @@ function compareIds (id1, id2) {
 | 
				
			|||||||
    }
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  Y.utils.compareIds = compareIds
 | 
					  Y.utils.compareIds = compareIds
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										63
									
								
								src/y.js
									
									
									
									
									
								
							
							
						
						
									
										63
									
								
								src/y.js
									
									
									
									
									
								
							@ -1,7 +1,63 @@
 | 
				
			|||||||
/* @flow */
 | 
					/* @flow */
 | 
				
			||||||
'use strict'
 | 
					'use strict'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					require('./Connector.js')(Y)
 | 
				
			||||||
 | 
					require('./Database.js')(Y)
 | 
				
			||||||
 | 
					require('./Transaction.js')(Y)
 | 
				
			||||||
 | 
					require('./Struct.js')(Y)
 | 
				
			||||||
 | 
					require('./Utils.js')(Y)
 | 
				
			||||||
 | 
					require('./Databases/RedBlackTree.js')(Y)
 | 
				
			||||||
 | 
					require('./Databases/Memory.js')(Y)
 | 
				
			||||||
 | 
					require('./Databases/IndexedDB.js')(Y)
 | 
				
			||||||
 | 
					require('./Connectors/Test.js')(Y)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var requiringModules = {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					module.exports = Y
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					Y.extend = function (name, value) {
 | 
				
			||||||
 | 
					  Y[name] = value
 | 
				
			||||||
 | 
					  var resolves = requiringModules[name]
 | 
				
			||||||
 | 
					  if (requiringModules[name] != null) {
 | 
				
			||||||
 | 
					    for (var i = 0; i < resolves.length; i++) {
 | 
				
			||||||
 | 
					      resolves[i]()
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    delete requiringModules[name]
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					require('./Types/Array.js')(Y)
 | 
				
			||||||
 | 
					require('./Types/Map.js')(Y)
 | 
				
			||||||
 | 
					require('./Types/TextBind.js')(Y)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
function Y (opts) {
 | 
					function Y (opts) {
 | 
				
			||||||
 | 
					  opts.types = opts.types != null ? opts.types : []
 | 
				
			||||||
 | 
					  var modules = [opts.db.name, opts.connector.name].concat(opts.types)
 | 
				
			||||||
 | 
					  var promises = []
 | 
				
			||||||
 | 
					  for (var i = 0; i < modules.length; i++) {
 | 
				
			||||||
 | 
					    if (Y[modules[i]] == null) {
 | 
				
			||||||
 | 
					      try {
 | 
				
			||||||
 | 
					        require(modules[i])(Y)
 | 
				
			||||||
 | 
					      } catch (e) {
 | 
				
			||||||
 | 
					        // module does not exist
 | 
				
			||||||
 | 
					        if (window != null) {
 | 
				
			||||||
 | 
					          if (requiringModules[modules[i]] == null) {
 | 
				
			||||||
 | 
					            var imported = document.createElement('script')
 | 
				
			||||||
 | 
					            var name = modules[i].toLowerCase()
 | 
				
			||||||
 | 
					            imported.src = opts.sourceDir + '/y-' + name + '/y-' + name + '.js'
 | 
				
			||||||
 | 
					            document.head.appendChild(imported)
 | 
				
			||||||
 | 
					            requiringModules[modules[i]] = []
 | 
				
			||||||
 | 
					          }
 | 
				
			||||||
 | 
					          promises.push(new Promise(function (resolve) {
 | 
				
			||||||
 | 
					            requiringModules[modules[i]].push(resolve)
 | 
				
			||||||
 | 
					          }))
 | 
				
			||||||
 | 
					        } else {
 | 
				
			||||||
 | 
					          throw e
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					      }
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  return Promise.all(promises).then(function () {
 | 
				
			||||||
    return new Promise(function (resolve) {
 | 
					    return new Promise(function (resolve) {
 | 
				
			||||||
      var yconfig = new YConfig(opts, function () {
 | 
					      var yconfig = new YConfig(opts, function () {
 | 
				
			||||||
        yconfig.db.whenUserIdSet(function () {
 | 
					        yconfig.db.whenUserIdSet(function () {
 | 
				
			||||||
@ -9,6 +65,7 @@ function Y (opts) {
 | 
				
			|||||||
        })
 | 
					        })
 | 
				
			||||||
      })
 | 
					      })
 | 
				
			||||||
    })
 | 
					    })
 | 
				
			||||||
 | 
					  })
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class YConfig {
 | 
					class YConfig {
 | 
				
			||||||
@ -49,9 +106,3 @@ class YConfig {
 | 
				
			|||||||
if (typeof window !== 'undefined') {
 | 
					if (typeof window !== 'undefined') {
 | 
				
			||||||
  window.Y = Y
 | 
					  window.Y = Y
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					 | 
				
			||||||
if (typeof YConcurrency_TestingMode !== 'undefined') {
 | 
					 | 
				
			||||||
  g.Y = Y //eslint-disable-line
 | 
					 | 
				
			||||||
  // debugger //eslint-disable-line
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
Y.utils = {}
 | 
					 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user