implemented named event handler

This commit is contained in:
Kevin Jahns 2017-07-05 17:01:21 +02:00
parent 7e4dedab38
commit 8abef69aa7
6 changed files with 66 additions and 21 deletions

12
package-lock.json generated
View File

@ -1032,6 +1032,12 @@
"integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=",
"dev": true "dev": true
}, },
"ez-async": {
"version": "1.0.0-alpha.1",
"resolved": "https://registry.npmjs.org/ez-async/-/ez-async-1.0.0-alpha.1.tgz",
"integrity": "sha1-ysNCuPqJAm7+c6Jg/p9rgE9J5H8=",
"dev": true
},
"fast-levenshtein": { "fast-levenshtein": {
"version": "2.0.6", "version": "2.0.6",
"resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz",
@ -2930,6 +2936,12 @@
} }
} }
}, },
"tag-dist-files": {
"version": "0.1.6",
"resolved": "https://registry.npmjs.org/tag-dist-files/-/tag-dist-files-0.1.6.tgz",
"integrity": "sha1-h64FrBQw1H2m76Hrx7Bw+QxnTVQ=",
"dev": true
},
"text-table": { "text-table": {
"version": "0.2.0", "version": "0.2.0",
"resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz",

View File

@ -6,16 +6,17 @@
"scripts": { "scripts": {
"lint": "standard", "lint": "standard",
"dist": "rollup -c rollup.dist.js", "dist": "rollup -c rollup.dist.js",
"serve": "concurrently 'serve ..' 'rollup -wc rollup.dist.js -o examples/bower_components/yjs/y.js'" "serve": "concurrently 'serve ..' 'rollup -wc rollup.dist.js -o examples/bower_components/yjs/y.js'",
"postversion": "npm run lint && npm run dist",
"postpublish": "tag-dist-files --overwrite-existing-tag"
}, },
"pre-commit": [ "files": [
"lint", "y.*"
"test"
], ],
"standard": { "standard": {
"ignore": [ "ignore": [
"./y.js", "/y.js",
"./y.js.map" "/y.js.map"
] ]
}, },
"repository": { "repository": {
@ -40,10 +41,10 @@
"homepage": "http://y-js.org", "homepage": "http://y-js.org",
"devDependencies": { "devDependencies": {
"babel-cli": "^6.24.1", "babel-cli": "^6.24.1",
"babel-preset-latest": "^6.24.1",
"babel-plugin-external-helpers": "^6.22.0", "babel-plugin-external-helpers": "^6.22.0",
"babel-plugin-transform-regenerator": "^6.24.1", "babel-plugin-transform-regenerator": "^6.24.1",
"babel-plugin-transform-runtime": "^6.23.0", "babel-plugin-transform-runtime": "^6.23.0",
"babel-preset-latest": "^6.24.1",
"chance": "^1.0.9", "chance": "^1.0.9",
"concurrently": "^3.4.0", "concurrently": "^3.4.0",
"rollup-plugin-babel": "^2.7.1", "rollup-plugin-babel": "^2.7.1",
@ -54,7 +55,8 @@
"rollup-plugin-uglify": "^1.0.2", "rollup-plugin-uglify": "^1.0.2",
"rollup-regenerator-runtime": "^6.23.1", "rollup-regenerator-runtime": "^6.23.1",
"rollup-watch": "^3.2.2", "rollup-watch": "^3.2.2",
"standard": "^10.0.2" "standard": "^10.0.2",
"tag-dist-files": "^0.1.6"
}, },
"dependencies": { "dependencies": {
"debug": "^2.6.8" "debug": "^2.6.8"

View File

@ -401,11 +401,11 @@ export default function extendDatabase (Y /* :any */) {
whenOperationsExist: any; whenOperationsExist: any;
*/ */
* tryExecute (op) { * tryExecute (op) {
this.store.addToDebug('yield* this.store.tryExecute.call(this, ', JSON.stringify(op), ')') this.store.addToDebug('yield * this.store.tryExecute.call(this, ', JSON.stringify(op), ')')
if (op.struct === 'Delete') { if (op.struct === 'Delete') {
yield * Y.Struct.Delete.execute.call(this, op) yield * Y.Struct.Delete.execute.call(this, op)
// this is now called in Transaction.deleteOperation! // this is now called in Transaction.deleteOperation!
// yield* this.store.operationAdded(this, op) // yield * this.store.operationAdded(this, op)
} else { } else {
// check if this op was defined // check if this op was defined
var defined = yield * this.getInsertion(op.id) var defined = yield * this.getInsertion(op.id)

View File

@ -162,14 +162,14 @@ export default function extendTransaction (Y) {
if (target.start != null) { if (target.start != null) {
// TODO: don't do it like this .. -.- // TODO: don't do it like this .. -.-
yield * this.deleteList(target.start) yield * this.deleteList(target.start)
// yield* this.deleteList(target.id) -- do not gc itself because this may still get referenced // yield * this.deleteList(target.id) -- do not gc itself because this may still get referenced
} }
if (target.map != null) { if (target.map != null) {
for (var name in target.map) { for (var name in target.map) {
yield * this.deleteList(target.map[name]) yield * this.deleteList(target.map[name])
} }
// TODO: here to.. (see above) // TODO: here to.. (see above)
// yield* this.deleteList(target.id) -- see above // yield * this.deleteList(target.id) -- see above
} }
if (target.opContent != null) { if (target.opContent != null) {
yield * this.deleteOperation(target.opContent) yield * this.deleteOperation(target.opContent)
@ -223,7 +223,7 @@ export default function extendTransaction (Y) {
*/ */
* markGarbageCollected (id, len) { * markGarbageCollected (id, len) {
// this.mem.push(["gc", id]); // this.mem.push(["gc", id]);
this.store.addToDebug('yield* this.markGarbageCollected(', id, ', ', len, ')') this.store.addToDebug('yield * this.markGarbageCollected(', id, ', ', len, ')')
var n = yield * this.markDeleted(id, len) var n = yield * this.markDeleted(id, len)
if (n.id[1] < id[1] && !n.gc) { if (n.id[1] < id[1] && !n.gc) {
// un-extend left // un-extend left
@ -294,8 +294,9 @@ export default function extendTransaction (Y) {
yield * this.ds.put(n) yield * this.ds.put(n)
} else { } else {
// already gc'd // already gc'd
throw new Error('Cannot happen! (it dit though.. :()') throw new Error(
// return n 'DS reached an inconsistent state. Please report this issue!'
)
} }
} }
} else { } else {
@ -418,7 +419,7 @@ export default function extendTransaction (Y) {
* reset origins of all right ops * reset origins of all right ops
*/ */
* garbageCollectOperation (id) { * garbageCollectOperation (id) {
this.store.addToDebug('yield* this.garbageCollectOperation(', id, ')') this.store.addToDebug('yield * this.garbageCollectOperation(', id, ')')
var o = yield * this.getOperation(id) var o = yield * this.getOperation(id)
yield * this.markGarbageCollected(id, (o != null && o.content != null) ? o.content.length : 1) // always mark gc'd yield * this.markGarbageCollected(id, (o != null && o.content != null) ? o.content.length : 1) // always mark gc'd
// if op exists, then clean that mess up.. // if op exists, then clean that mess up..
@ -475,7 +476,7 @@ export default function extendTransaction (Y) {
right.origin = neworigin right.origin = neworigin
// search until you find origin pointer to the left of o // search until you find origin pointer to the left of o
if (right.right != null) { if (right.right != null) {
var i = yield* this.getOperation(right.right) var i = yield * this.getOperation(right.right)
var ids = [o.id, o.right] var ids = [o.id, o.right]
while (ids.some(function (id) { while (ids.some(function (id) {
return Y.utils.compareIds(id, i.origin) return Y.utils.compareIds(id, i.origin)
@ -483,14 +484,14 @@ export default function extendTransaction (Y) {
if (Y.utils.compareIds(i.origin, o.id)) { if (Y.utils.compareIds(i.origin, o.id)) {
// reset origin of i // reset origin of i
i.origin = neworigin i.origin = neworigin
yield* this.setOperation(i) yield * this.setOperation(i)
} }
// get next i // get next i
if (i.right == null) { if (i.right == null) {
break break
} else { } else {
ids.push(i.id) ids.push(i.id)
i = yield* this.getOperation(i.right) i = yield * this.getOperation(i.right)
} }
} }
} }
@ -1086,7 +1087,7 @@ export default function extendTransaction (Y) {
// or the o that has no origin to the right of op // or the o that has no origin to the right of op
// (this is why we use the ids array) // (this is why we use the ids array)
while (o.right != null) { while (o.right != null) {
var right = yield* this.getOperation(o.right) var right = yield * this.getOperation(o.right)
if (o.right[1] < (startSS[o.right[0]] || 0) || !ids.some(function (id) { if (o.right[1] < (startSS[o.right[0]] || 0) || !ids.some(function (id) {
return Y.utils.compareIds(id, right.origin) return Y.utils.compareIds(id, right.origin)
})) { })) {

View File

@ -42,6 +42,32 @@ export default function Utils (Y) {
} }
} }
class NamedEventHandler {
constructor () {
this._eventListener = {}
}
on (name, f) {
if (this._eventListener[name] == null) {
this._eventListener[name] = []
}
this._eventListener[name].push(f)
}
off (name, f) {
if (name == null || f == null) {
throw new Error('You must specify event name and function!')
}
let listener = this._eventListener[name] || []
this._eventListener[name] = listener.filter(e => e !== f)
}
emit (name, value) {
(this._eventListener[name] || []).forEach(l => l(value))
}
destroy () {
this._eventListener = null
}
}
Y.utils.NamedEventHandler = NamedEventHandler
class EventListenerHandler { class EventListenerHandler {
constructor () { constructor () {
this.eventListeners = [] this.eventListeners = []

View File

@ -144,7 +144,7 @@ export default function Y (opts/* :YOptions */) /* :Promise<YConfig> */ {
}) })
} }
class YConfig { class YConfig extends Y.utils.NamedEventHandler {
/* :: /* ::
db: Y.AbstractDatabase; db: Y.AbstractDatabase;
connector: Y.AbstractConnector; connector: Y.AbstractConnector;
@ -152,6 +152,7 @@ class YConfig {
options: Object; options: Object;
*/ */
constructor (opts, callback) { constructor (opts, callback) {
super()
this.options = opts this.options = opts
this.db = new Y[opts.db.name](this, opts.db) this.db = new Y[opts.db.name](this, opts.db)
this.connector = new Y[opts.connector.name](this, opts.connector) this.connector = new Y[opts.connector.name](this, opts.connector)
@ -215,6 +216,9 @@ class YConfig {
} else { } else {
return Promise.resolve() return Promise.resolve()
} }
}).then(() => {
// remove existing event listener
super.destroy()
}) })
} }
close () { close () {