diff --git a/src/utils/AttributionManager.js b/src/utils/AttributionManager.js index f363d98f..869110ab 100644 --- a/src/utils/AttributionManager.js +++ b/src/utils/AttributionManager.js @@ -175,8 +175,20 @@ export class DiffAttributionManager { this._prevBOH = prevDoc.on('beforeObserverCalls', tr => { insertIntoIdSet(_prevDocInserts, tr.insertSet) insertIntoIdSet(prevDocDeletes, tr.deleteSet) - this.inserts = diffIdMap(this.inserts, tr.insertSet) - this.deletes = diffIdMap(this.deletes, tr.deleteSet) + if (tr.insertSet.clients.size < 2) { + tr.insertSet.forEach((idrange, client) => { + this.inserts.delete(client, idrange.clock, idrange.len) + }) + } else { + this.inserts = diffIdMap(this.inserts, tr.insertSet) + } + if (tr.deleteSet.clients.size < 2) { + tr.deleteSet.forEach((attrRange, client) => { + this.deletes.delete(client, attrRange.clock, attrRange.len) + }) + } else { + this.deletes = diffIdMap(this.deletes, tr.deleteSet) + } // @todo fire update ranges on `tr.insertSet` and `tr.deleteSet` }) this._destroyHandler = nextDoc.on('destroy', this.destroy.bind(this)) diff --git a/src/utils/IdMap.js b/src/utils/IdMap.js index 9b168717..f8c68492 100644 --- a/src/utils/IdMap.js +++ b/src/utils/IdMap.js @@ -321,6 +321,17 @@ export class IdMap { this.attrs = new Set() } + /** + * @param {(attrRange:AttrRange, client:number) => void} f + */ + forEach (f) { + this.clients.forEach((ranges, client) => { + ranges.getIds().forEach((range) => { + f(range, client) + }) + }) + } + /** * @param {ID} id * @return {boolean} diff --git a/src/utils/IdSet.js b/src/utils/IdSet.js index d9f06d81..5e236b73 100644 --- a/src/utils/IdSet.js +++ b/src/utils/IdSet.js @@ -113,6 +113,17 @@ export class IdSet { this.clients = new Map() } + /** + * @param {(idrange:IdRange, client:number) => void} f + */ + forEach (f) { + this.clients.forEach((ranges, client) => { + ranges.getIds().forEach((range) => { + f(range, client) + }) + }) + } + /** * @param {ID} id * @return {boolean}