[js][database] synctree cleanup

This commit is contained in:
Salakar 2017-08-16 21:43:24 +01:00
parent 4e78c5373b
commit 5ccbd9f369
3 changed files with 36 additions and 35 deletions

View File

@ -1,6 +1,8 @@
import EventEmitter from 'EventEmitter'; import EventEmitter from 'EventEmitter';
import { Platform, NativeModules } from 'react-native'; import { Platform, NativeModules } from 'react-native';
import SyncTree from './utils/SyncTree';
const DEFAULT_APP_NAME = Platform.OS === 'ios' ? '__FIRAPP_DEFAULT' : '[DEFAULT]'; const DEFAULT_APP_NAME = Platform.OS === 'ios' ? '__FIRAPP_DEFAULT' : '[DEFAULT]';
export default { export default {

View File

@ -20,6 +20,7 @@ import {
import INTERNALS from './../../internals'; import INTERNALS from './../../internals';
// track all event registrations by path // track all event registrations by path
let listeners = 0;
/** /**
* Enum for event types * Enum for event types
@ -70,7 +71,6 @@ export default class Reference extends ReferenceBase {
constructor(database: Object, path: string, existingModifiers?: Array<DatabaseModifier>) { constructor(database: Object, path: string, existingModifiers?: Array<DatabaseModifier>) {
super(path, database); super(path, database);
this._promise = null; this._promise = null;
this._listeners = 0;
this._refListeners = {}; this._refListeners = {};
this._database = database; this._database = database;
this._query = new Query(this, path, existingModifiers); this._query = new Query(this, path, existingModifiers);
@ -517,7 +517,7 @@ export default class Reference extends ReferenceBase {
* @return {string} * @return {string}
*/ */
_getRegistrationKey(eventType) { _getRegistrationKey(eventType) {
return `$${this._database._appName}$${this.path}$${this._query.queryIdentifier()}$${this._listeners}$${eventType}`; return `$${this._database._appName}$/${this.path}$${this._query.queryIdentifier()}$${listeners}$${eventType}`;
} }
/** /**
@ -528,7 +528,7 @@ export default class Reference extends ReferenceBase {
* @private * @private
*/ */
_getRefKey() { _getRefKey() {
return `$${this._database._appName}$${this.path}$${this._query.queryIdentifier()}`; return `$${this._database._appName}$/${this.path}$${this._query.queryIdentifier()}`;
} }
/** /**
@ -636,18 +636,16 @@ export default class Reference extends ReferenceBase {
const eventRegistrationKey = this._getRegistrationKey(eventType); const eventRegistrationKey = this._getRegistrationKey(eventType);
const registrationCancellationKey = `${eventRegistrationKey}$cancelled`; const registrationCancellationKey = `${eventRegistrationKey}$cancelled`;
const _context = (cancelCallbackOrContext && !isFunction(cancelCallbackOrContext)) ? cancelCallbackOrContext : context; const _context = (cancelCallbackOrContext && !isFunction(cancelCallbackOrContext)) ? cancelCallbackOrContext : context;
const registrationObj = {
this._syncTree.addRegistration(
{
eventType, eventType,
ref: this, ref: this,
path: this.path, path: this.path,
key: this._getRefKey(), key: this._getRefKey(),
appName: this._database._appName, appName: this._database._appName,
registration: eventRegistrationKey, eventRegistrationKey,
}, };
_context ? callback.bind(_context) : callback,
); this._syncTree.addRegistration(registrationObj, _context ? callback.bind(_context) : callback);
if (isFunction(cancelCallbackOrContext)) { if (isFunction(cancelCallbackOrContext)) {
// cancellations have their own separate registration // cancellations have their own separate registration
@ -661,7 +659,7 @@ export default class Reference extends ReferenceBase {
key: this._getRefKey(), key: this._getRefKey(),
appName: this._database._appName, appName: this._database._appName,
eventType: `${eventType}$cancelled`, eventType: `${eventType}$cancelled`,
registration: registrationCancellationKey, eventRegistrationKey: registrationCancellationKey,
}, },
_context ? cancelCallbackOrContext.bind(_context) : cancelCallbackOrContext, _context ? cancelCallbackOrContext.bind(_context) : cancelCallbackOrContext,
); );
@ -674,16 +672,17 @@ export default class Reference extends ReferenceBase {
key: this._getRefKey(), key: this._getRefKey(),
appName: this._database._appName, appName: this._database._appName,
modifiers: this._query.getModifiers(), modifiers: this._query.getModifiers(),
hasCancellationCallback: isFunction(cancelCallbackOrContext),
registration: { registration: {
eventRegistrationKey, eventRegistrationKey,
key: registrationObj.key,
registrationCancellationKey, registrationCancellationKey,
hasCancellationCallback: isFunction(cancelCallbackOrContext),
}, },
}); });
// increment number of listeners - just s short way of making // increment number of listeners - just s short way of making
// every registration unique per .on() call // every registration unique per .on() call
this._listeners = this._listeners + 1; listeners += 1;
// return original unbound successCallback for // return original unbound successCallback for
// the purposes of calling .off(eventType, callback) at a later date // the purposes of calling .off(eventType, callback) at a later date
@ -755,4 +754,3 @@ export default class Reference extends ReferenceBase {
return INTERNALS.SyncTree; return INTERNALS.SyncTree;
} }
} }

View File

@ -11,7 +11,7 @@ type Registration = {
once?: Boolean, once?: Boolean,
appName: String, appName: String,
eventType: String, eventType: String,
registration: String, eventRegistrationKey: String,
ref: DatabaseReference, ref: DatabaseReference,
} }
@ -53,7 +53,8 @@ export default class SyncTree {
* @private * @private
*/ */
_handleValueEvent(event) { _handleValueEvent(event) {
const { eventRegistrationKey } = event.registration; // console.log('SyncTree.VALUE >>>', event);
const { key, eventRegistrationKey } = event.registration;
const registration = this.getRegistration(eventRegistrationKey); const registration = this.getRegistration(eventRegistrationKey);
if (!registration) { if (!registration) {
@ -61,10 +62,7 @@ export default class SyncTree {
// notify native that the registration // notify native that the registration
// no longer exists so it can remove // no longer exists so it can remove
// the native listeners // the native listeners
return this._databaseNative.off({ return this._databaseNative.off(key, eventRegistrationKey);
key: event.key,
eventRegistrationKey,
});
} }
const { snapshot, previousChildName } = event.data; const { snapshot, previousChildName } = event.data;
@ -85,6 +83,7 @@ export default class SyncTree {
* @private * @private
*/ */
_handleErrorEvent(event) { _handleErrorEvent(event) {
// console.log('SyncTree.ERROR >>>', event);
const { code, message } = event.error; const { code, message } = event.error;
const { eventRegistrationKey, registrationCancellationKey } = event.registration; const { eventRegistrationKey, registrationCancellationKey } = event.registration;
@ -207,18 +206,24 @@ export default class SyncTree {
* @return {String} * @return {String}
*/ */
addRegistration(parameters: Registration, listener): String { addRegistration(parameters: Registration, listener): String {
const { path, eventType, registration, once } = parameters; const { path, eventType, eventRegistrationKey, once } = parameters;
if (!this._tree[path]) this._tree[path] = {}; if (!this._tree[path]) this._tree[path] = {};
if (!this._tree[path][eventType]) this._tree[path][eventType] = {}; if (!this._tree[path][eventType]) this._tree[path][eventType] = {};
this._tree[path][eventType][registration] = 0; this._tree[path][eventType][eventRegistrationKey] = 0;
this._reverseLookup[registration] = Object.assign({}, parameters); this._reverseLookup[eventRegistrationKey] = Object.assign({}, parameters);
if (once) INTERNALS.SharedEventEmitter.once(registration, this._onOnceRemoveRegistration(registration, listener)); if (once) {
else INTERNALS.SharedEventEmitter.addListener(registration, listener); INTERNALS.SharedEventEmitter.once(
eventRegistrationKey,
this._onOnceRemoveRegistration(eventRegistrationKey, listener),
);
} else {
INTERNALS.SharedEventEmitter.addListener(eventRegistrationKey, listener);
}
return registration; return eventRegistrationKey;
} }
/** /**
@ -246,11 +251,7 @@ export default class SyncTree {
// automatically unsubscribed on native when the first event is sent // automatically unsubscribed on native when the first event is sent
const registrationObj = this._reverseLookup[registration]; const registrationObj = this._reverseLookup[registration];
if (registrationObj && !once) { if (registrationObj && !once) {
this._databaseNative.off({ this._databaseNative.off(registrationObj.key, registration);
key: registrationObj.key,
eventType: registrationObj.eventType,
eventRegistrationKey: registration,
});
} }
delete this._tree[path][eventType][registration]; delete this._tree[path][eventType][registration];