[android][database] cleanup & implement .off() native functionality
This commit is contained in:
parent
e4d27029b9
commit
887823162a
|
@ -13,7 +13,6 @@ import com.facebook.react.bridge.ReactApplicationContext;
|
|||
import com.facebook.react.bridge.ReactContextBaseJavaModule;
|
||||
|
||||
import com.google.firebase.FirebaseApp;
|
||||
import com.google.firebase.database.ChildEventListener;
|
||||
import com.google.firebase.database.MutableData;
|
||||
import com.google.firebase.database.OnDisconnect;
|
||||
import com.google.firebase.database.ServerValue;
|
||||
|
@ -22,7 +21,6 @@ import com.google.firebase.database.DataSnapshot;
|
|||
import com.google.firebase.database.DatabaseError;
|
||||
import com.google.firebase.database.FirebaseDatabase;
|
||||
import com.google.firebase.database.DatabaseReference;
|
||||
import com.google.firebase.database.ValueEventListener;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
@ -33,40 +31,13 @@ import io.invertase.firebase.Utils;
|
|||
|
||||
public class RNFirebaseDatabase extends ReactContextBaseJavaModule {
|
||||
private static final String TAG = "RNFirebaseDatabase";
|
||||
private HashMap<String, ChildEventListener> childEventListeners;
|
||||
private HashMap<String, ValueEventListener> valueEventListeners;
|
||||
private HashMap<String, RNFirebaseDatabaseReference> references = new HashMap<String, RNFirebaseDatabaseReference>();
|
||||
private HashMap<String, RNFirebaseDatabaseReference> references = new HashMap<>();
|
||||
private SparseArray<RNFirebaseTransactionHandler> transactionHandlers = new SparseArray<>();
|
||||
|
||||
RNFirebaseDatabase(ReactApplicationContext reactContext) {
|
||||
super(reactContext);
|
||||
childEventListeners = new HashMap<String, ChildEventListener>();
|
||||
valueEventListeners = new HashMap<String, ValueEventListener>();
|
||||
}
|
||||
|
||||
Boolean hasValueEventListener(String queryKey) {
|
||||
return valueEventListeners.containsKey(queryKey);
|
||||
}
|
||||
|
||||
Boolean hasChildEventListener(String queryKey) {
|
||||
return childEventListeners.containsKey(queryKey);
|
||||
}
|
||||
|
||||
void addValueEventListener(String queryKey, ValueEventListener listener) {
|
||||
valueEventListeners.put(queryKey, listener);
|
||||
}
|
||||
|
||||
void addChildEventListener(String queryKey, ChildEventListener listener) {
|
||||
childEventListeners.put(queryKey, listener);
|
||||
}
|
||||
|
||||
void removeValueEventListener(String queryKey) {
|
||||
valueEventListeners.remove(queryKey);
|
||||
}
|
||||
|
||||
void removeChildEventListener(String queryKey) {
|
||||
childEventListeners.remove(queryKey);
|
||||
}
|
||||
|
||||
/*
|
||||
* REACT NATIVE METHODS
|
||||
|
@ -427,17 +398,29 @@ public class RNFirebaseDatabase extends ReactContextBaseJavaModule {
|
|||
*/
|
||||
@ReactMethod
|
||||
public void on(String appName, ReadableMap props) {
|
||||
getInternalReferenceForApp(appName, props).on(
|
||||
this,
|
||||
props.getString("eventType"),
|
||||
props.getMap("registration")
|
||||
);
|
||||
getInternalReferenceForApp(appName, props)
|
||||
.on(
|
||||
this,
|
||||
props.getString("eventType"),
|
||||
props.getMap("registration")
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Removes the specified event registration key.
|
||||
* If the ref no longer has any listeners the the ref is removed.
|
||||
*
|
||||
* @param key
|
||||
* @param eventRegistrationKey
|
||||
*/
|
||||
@ReactMethod
|
||||
public void off(String appName, ReadableMap args) {
|
||||
public void off(String key, String eventRegistrationKey) {
|
||||
RNFirebaseDatabaseReference nativeRef = references.get(key);
|
||||
nativeRef.removeEventListener(eventRegistrationKey);
|
||||
|
||||
if (!nativeRef.hasListeners()) {
|
||||
references.remove(key);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -463,27 +446,6 @@ public class RNFirebaseDatabase extends ReactContextBaseJavaModule {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* React Method - returns this module name
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public String getName() {
|
||||
return "RNFirebaseDatabase";
|
||||
}
|
||||
|
||||
/**
|
||||
* React Native constants for RNFirebaseDatabase
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Map<String, Object> getConstants() {
|
||||
final Map<String, Object> constants = new HashMap<>();
|
||||
constants.put("serverValueTimestamp", ServerValue.TIMESTAMP);
|
||||
return constants;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a database instance for a specific firebase app instance
|
||||
|
@ -533,6 +495,8 @@ public class RNFirebaseDatabase extends ReactContextBaseJavaModule {
|
|||
}
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param appName
|
||||
* @param props
|
||||
* @return
|
||||
|
@ -657,4 +621,26 @@ public class RNFirebaseDatabase extends ReactContextBaseJavaModule {
|
|||
errorMap.putString("message", message);
|
||||
return errorMap;
|
||||
}
|
||||
|
||||
/**
|
||||
* React Method - returns this module name
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public String getName() {
|
||||
return "RNFirebaseDatabase";
|
||||
}
|
||||
|
||||
/**
|
||||
* React Native constants for RNFirebaseDatabase
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public Map<String, Object> getConstants() {
|
||||
final Map<String, Object> constants = new HashMap<>();
|
||||
constants.put("serverValueTimestamp", ServerValue.TIMESTAMP);
|
||||
return constants;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
package io.invertase.firebase.database;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.List;
|
||||
|
||||
|
@ -23,20 +24,21 @@ import com.google.firebase.database.ValueEventListener;
|
|||
import io.invertase.firebase.Utils;
|
||||
|
||||
class RNFirebaseDatabaseReference {
|
||||
private static final String TAG = "RNFirebaseDBReference";
|
||||
|
||||
private String key;
|
||||
private Query query;
|
||||
private String path;
|
||||
private String appName;
|
||||
private ReactContext reactContext;
|
||||
|
||||
private static final String TAG = "RNFirebaseDBReference";
|
||||
private HashMap<String, ChildEventListener> childEventListeners;
|
||||
private HashMap<String, ValueEventListener> valueEventListeners;
|
||||
|
||||
Query getQuery() {
|
||||
return query;
|
||||
}
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param context
|
||||
* @param app
|
||||
* @param refKey
|
||||
|
@ -46,9 +48,67 @@ class RNFirebaseDatabaseReference {
|
|||
RNFirebaseDatabaseReference(ReactContext context, String app, String refKey, String refPath, ReadableArray modifiersArray) {
|
||||
key = refKey;
|
||||
appName = app;
|
||||
path = refPath;
|
||||
reactContext = context;
|
||||
query = buildDatabaseQueryAtPathAndModifiers(path, modifiersArray);
|
||||
childEventListeners = new HashMap<String, ChildEventListener>();
|
||||
valueEventListeners = new HashMap<String, ValueEventListener>();
|
||||
query = buildDatabaseQueryAtPathAndModifiers(refPath, modifiersArray);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true/false whether this internal ref has a specific listener by eventRegistrationKey.
|
||||
*
|
||||
* @param eventRegistrationKey
|
||||
* @return
|
||||
*/
|
||||
private Boolean hasEventListener(String eventRegistrationKey) {
|
||||
return valueEventListeners.containsKey(eventRegistrationKey) || childEventListeners.containsKey(eventRegistrationKey);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true/false whether this internal ref has any child or value listeners.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
Boolean hasListeners() {
|
||||
return valueEventListeners.size() > 0 || childEventListeners.size() > 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param eventRegistrationKey
|
||||
*/
|
||||
void removeEventListener(String eventRegistrationKey) {
|
||||
if (valueEventListeners.containsKey(eventRegistrationKey)) {
|
||||
query.removeEventListener(valueEventListeners.get(eventRegistrationKey));
|
||||
valueEventListeners.remove(eventRegistrationKey);
|
||||
}
|
||||
|
||||
if (childEventListeners.containsKey(eventRegistrationKey)) {
|
||||
query.removeEventListener(childEventListeners.get(eventRegistrationKey));
|
||||
childEventListeners.remove(eventRegistrationKey);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param eventRegistrationKey
|
||||
* @param listener
|
||||
*/
|
||||
private void addEventListener(String eventRegistrationKey, ValueEventListener listener) {
|
||||
valueEventListeners.put(eventRegistrationKey, listener);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param eventRegistrationKey
|
||||
* @param listener
|
||||
*/
|
||||
private void addEventListener(String eventRegistrationKey, ChildEventListener listener) {
|
||||
childEventListeners.put(eventRegistrationKey, listener);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -71,7 +131,6 @@ class RNFirebaseDatabaseReference {
|
|||
};
|
||||
|
||||
query.addListenerForSingleValueEvent(onceValueEventListener);
|
||||
|
||||
Log.d(TAG, "Added OnceValueEventListener for key: " + key);
|
||||
}
|
||||
|
||||
|
@ -160,6 +219,8 @@ class RNFirebaseDatabaseReference {
|
|||
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param registration
|
||||
* @param eventType
|
||||
* @param database
|
||||
|
@ -168,7 +229,7 @@ class RNFirebaseDatabaseReference {
|
|||
final String eventRegistrationKey = registration.getString("eventRegistrationKey");
|
||||
final String registrationCancellationKey = registration.getString("registrationCancellationKey");
|
||||
|
||||
if (!database.hasChildEventListener(eventRegistrationKey)) {
|
||||
if (!hasEventListener(eventRegistrationKey)) {
|
||||
ChildEventListener childEventListener = new ChildEventListener() {
|
||||
@Override
|
||||
public void onChildAdded(DataSnapshot dataSnapshot, String previousChildName) {
|
||||
|
@ -200,25 +261,26 @@ class RNFirebaseDatabaseReference {
|
|||
|
||||
@Override
|
||||
public void onCancelled(DatabaseError error) {
|
||||
query.removeEventListener(this);
|
||||
database.removeChildEventListener(eventRegistrationKey);
|
||||
removeEventListener(eventRegistrationKey);
|
||||
handleDatabaseError(registration, error);
|
||||
}
|
||||
};
|
||||
|
||||
database.addChildEventListener(eventRegistrationKey, childEventListener);
|
||||
addEventListener(eventRegistrationKey, childEventListener);
|
||||
query.addChildEventListener(childEventListener);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* TODO
|
||||
*
|
||||
* @param registration
|
||||
*/
|
||||
private void addValueEventListener(final ReadableMap registration, final RNFirebaseDatabase database) {
|
||||
final String eventRegistrationKey = registration.getString("eventRegistrationKey");
|
||||
final String registrationCancellationKey = registration.getString("registrationCancellationKey");
|
||||
|
||||
if (!database.hasValueEventListener(eventRegistrationKey)) {
|
||||
if (!hasEventListener(eventRegistrationKey)) {
|
||||
ValueEventListener valueEventListener = new ValueEventListener() {
|
||||
@Override
|
||||
public void onDataChange(DataSnapshot dataSnapshot) {
|
||||
|
@ -227,13 +289,12 @@ class RNFirebaseDatabaseReference {
|
|||
|
||||
@Override
|
||||
public void onCancelled(DatabaseError error) {
|
||||
query.removeEventListener(this);
|
||||
database.removeValueEventListener(eventRegistrationKey);
|
||||
removeEventListener(eventRegistrationKey);
|
||||
handleDatabaseError(registration, error);
|
||||
}
|
||||
};
|
||||
|
||||
database.addValueEventListener(eventRegistrationKey, valueEventListener);
|
||||
addEventListener(eventRegistrationKey, valueEventListener);
|
||||
query.addValueEventListener(valueEventListener);
|
||||
}
|
||||
}
|
||||
|
@ -271,44 +332,6 @@ class RNFirebaseDatabaseReference {
|
|||
Utils.sendEvent(reactContext, "database_sync_event", event);
|
||||
}
|
||||
|
||||
|
||||
// todo cleanup below
|
||||
|
||||
// void removeEventListener(int listenerId, String eventName) {
|
||||
// if ("value".equals(eventName)) {
|
||||
// removeValueEventListener(listenerId);
|
||||
// } else {
|
||||
// removeChildEventListener(listenerId);
|
||||
// }
|
||||
// }
|
||||
|
||||
// boolean hasListeners() {
|
||||
// return childEventListeners.size() > 0 || valueEventListeners.size() > 0;
|
||||
// }
|
||||
//
|
||||
// public void cleanup() {
|
||||
// Log.d(TAG, "cleaning up database reference " + this);
|
||||
// this.removeChildEventListener(null);
|
||||
// this.removeValueEventListener(null);
|
||||
// }
|
||||
|
||||
// private void removeChildEventListener(Integer listenerId) {
|
||||
// ChildEventListener listener = childEventListeners.get(listenerId);
|
||||
// if (listener != null) {
|
||||
// query.removeEventListener(listener);
|
||||
// childEventListeners.remove(listenerId);
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// private void removeValueEventListener(Integer listenerId) {
|
||||
// ValueEventListener listener = valueEventListeners.get(listenerId);
|
||||
// if (listener != null) {
|
||||
// query.removeEventListener(listener);
|
||||
// valueEventListeners.delete(listenerId);
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
private Query buildDatabaseQueryAtPathAndModifiers(String path, ReadableArray modifiers) {
|
||||
FirebaseDatabase firebaseDatabase = RNFirebaseDatabase.getDatabaseForApp(appName);
|
||||
|
||||
|
|
Loading…
Reference in New Issue