How to merge two hashmap data fetched from firebase in android - java

I have two nodes Users and Plants
Users
|
|-plantId
|
|-image
|
|-imageLink
|-plantId
|
|-image
|
|-imageLink
Plants
|-plantId
|
|-collectedPlant
|
|-plantCount
The plantid in users and plants will be same. I need to get a HashMap containing plant id-imagelink and plantCount.
I have the two nodes data separately with me. Is there a simple way to solve it?

To solve this according to the edited database structure and assuming that the plantCount property is defined as a Long, please use the following code:
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference imageRef = rootRef.child("Users").child("plantId").child("image");
ValueEventListener valueEventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot ds : dataSnapshot.getChildren()) {
String imageLink = ds.child("imageLink").getValue(String.class);
DatabaseReference collectedPlantRef = rootRef.child("Plants").child("plantId").child("collectedPlant");
ValueEventListener eventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
Map<String, Long> map = new HashMap<>();
for(DataSnapshot dSnapshot : dataSnapshot.getChildren()) {
Long plantCount = dSnapshot.child("plantCount").getValue(Long.class);
map.put(imageLink, plantCount);
}
//Do what you want with this Map.
}
#Override
public void onCancelled(DatabaseError databaseError) {}
};
collectedPlantRef.addListenerForSingleValueEvent(eventListener);
}
}
#Override
public void onCancelled(DatabaseError databaseError) {}
};
imageRef.addListenerForSingleValueEvent(valueEventListener);
As you can see, I have used nested queries in order to get the Map that you are looking for.

Related

Getting Data from Firebase realtime database, Android Studio, Java

I am looking for a way to get data from the firebase real-time database in a format like an array[] or a String.
My database looks like this:
Link to image of database
Or:
Database
|
-->Users
|
-->UID1
-->UID2
This is at the root of the database
I want to get a list of all of the UIDs in the "Users" child.
This is the code I have so far and am a bit stuck on:
DatabaseReference databaseReference = firebaseDatabase.getReference("Users");
databaseReference.addValueEventListener(
new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
String UIDs = dataSnapshot.getValue(String.class);
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
});
I am a bit of a rookie as it comes to java, android studio, and firebase. I am trying to get the data in a format I know how to use like a String or an Array[] of Strings. I looked around if other people had maybe asked the same question, but I could get the answers to those questions to work/didn't understand them.
Thanks in advance for your time!
To get the a list of uids, please use the following code:
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference usersRef = rootRef.child("Users");
ValueEventListener valueEventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
List<String> list = new ArrayList<>();
for(DataSnapshot ds : dataSnapshot.getChildren()) {
String uid = ds.getKey();
list.add(uid);
}
//Do what you need to do with your list
}
#Override
public void onCancelled(#NonNull DatabaseError databaseError) {
Log.d(TAG, databaseError.getMessage()); //Don't ignore errors!
}
};
usersRef.addListenerForSingleValueEvent(valueEventListener);
I recommend you to use the list only inside the callback otherwise it will be empty. If you want to use it outside the onDataChange() method, I recommend you see the last part of my anwser from this post in which I have explained how it can be done using a custom callback. You can also take a look at this video for a better understanding.
For your above question I will give both ways: ArrayList or String with delimiters
ArrayList<String> uids = new ArrayList<String>();
FirebaseDatabase.getInstance().getReference("Users").addValueEventListener(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
if (dataSnapshot.exists()) {
for(DataSnapshot snapshot : dataSnapshot.getChildren()) {
uids.add(snapshot.getKey());
}
}
}
#Override
public void onCancelled(DatabaseError error) {
}
});
For String
String uids = "";
FirebaseDatabase.getInstance().getReference("Users").addValueEventListener(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
if (dataSnapshot.exists()) {
for(DataSnapshot snapshot : dataSnapshot.getChildren()) {
uids += snapshot.getKey() + ",";
}
}
}
#Override
public void onCancelled(DatabaseError error) {
}
});
This gives an output such as: uid1,uid2,uid3,.....uidn,
You can try this:
DatabaseReference ref=
FirebaseDatabase.getInstance().getReference("Users");
ref.addValueEventListener(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
if (dataSnapshot.exists()) {
int i = 0;
for(DataSnapshot d : dataSnapshot.getChildren()) {
name[i] = d.getKey();
i++;
}
}
}//onDataChange
#Override
public void onCancelled(DatabaseError error) {
}//onCancelled
});
name[] is an array of strings!

How to getChildren more than once and save the parent node

Assume my database has the following structure:
data
|___randomId1
| |_________randomData1
| |______Key1: value
| |______Key2: value
|___randomId2
|_________randomData2
|______Key1: value
|______Key2: value
And I want to iterate to get all values, and also save the parent id (randomId1, randomId2). How can I loop through? right now I have the following:
ValueEventListener eventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot ds : dataSnapshot.getChildren()) {
// what to put here to get the values and also save the ids?
}
}
You see that each randomData has the same map (Key1 and Key2).
To solve this, you need use two nested loops like in the following lines of code:
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference dataRef = rootRef.child("data");
ValueEventListener valueEventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot dSnapshot : dataSnapshot.getChildren()) {
String parentKey = dSnapshot.getKey();
for(DataSnapshot ds : dSnapshot.getChildren()) {
String key = ds.getKey();
String key1 = ds.child("Key1").getValue(String.class);
String key2 = ds.child("Key2").getValue(String.class);
Log.d(TAG, key1 + " / " + key2);
}
}
}
#Override
public void onCancelled(#NonNull DatabaseError databaseError) {
Log.d(TAG, databaseError.getMessage()); //Don't ignore errors!
}
};
dataRef.addListenerForSingleValueEvent(valueEventListener);

How to retrieve data for a specific child in firebase database - android studio/ java?

I want to retrieve data for a specific child, how I can write the code? I try a lot, but it did not work:"([ like in my database here how to get the tasks for specific child like lubna and gets all it's child?
Initialize class variables:
private DatabaseReference mDatabase;
mDatabase = FirebaseDatabase.getInstance().getReference();
private DatabaseReference lubnaRef = mDatabase.child("tasks/Lubna");
And then for testing purposes I am assuming you are calling this in your onCreate method of your activity, you'd add the following assuming you do not have a data model for it:
lubnaRef.addListenerForSingleValueEvent(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
//These are all of your children.
Map<String, Object> lubna = (Map<String, Object>) dataSnapshot.getValue();
for (String childKey: lubna.keySet()) {
//childKey is your "-LQka.. and so on"
//Your current object holds all the variables in your picture.
Map<String, Object> currentLubnaObject = (Map<String, Object>) lubna.get(childKey);
//You can access each variable like so: String variableName = (String) currentLubnaObject.get("INSERT_VARIABLE_HERE"); //data, description, taskid, time, title
}
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
});
To solve this, please use the following lines of code:
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference lubnaRef = rootRef.child("tasks").child("Lubna");
ValueEventListener valueEventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot ds : dataSnapshot.getChildren()) {
String title = ds.child("title").getValue(String.class);
Log.d(TAG, title);
}
}
#Override
public void onCancelled(#NonNull DatabaseError databaseError) {
Log.d(TAG, databaseError.getMessage());
}
};
lubnaRef.addListenerForSingleValueEvent(valueEventListener);
In the same way you get the title, you can also get the other values. The output in your logcat will be:
Homework
//and so on

Firebase database retreiving value, is this possible

I have this code:
DatabaseReference mdatabase = FirebaseDatabase.getInstance().getReference("allmessages");
mdatabase.child(mAuth.getCurrentUser().getUid()).child(userID).child(uploadID).push().setValue("somevalue");
Then in another class I have this code:
DatabaseReference mdatabase = FirebaseDatabase.getInstance().getReference("allmessages");
mdatabase.child(mAuth.getCurrentUser().getUid()).addValueEventListener(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
//Loop through all files in Uploads DataBase
for(DataSnapshot postSnapshot : dataSnapshot.getChildren()){
AllChatMessagesGet allChatMessagesGet = postSnapshot.getValue(AllChatMessagesGet.class);
is it possible for me to get all value under mdatabase.child(mAuth.getCurrentUser().getUid()).child(userID).child(uploadID).push().setValue("somevalue"); by the code I used above.
Because it doesn't retrieve me anything back. I thought that the above code in addValueEventListener would go trough all child classes of mAuth.getCurrentUser().getUid() and retrive me the "somevalue".
But it doesn't. So how do I retrieve "somevalue". Is there any other way? because the codes are written in different classes and I dont know how to get .Child(userID) and .Child(uploadID) it would be problematic for me.
is there anyway for me to retrive all childrens of mdatabase.child(mAuth.getCurrentUser().getUid()) and their values that exist some child below it.
According to your comments, to get those ids that starts with -LD under -LCzWNw0nlC3GKsnPH8B node using only rootRef.child("AllChatMessages").child(uid), please use the followig code:
String uid = FirebaseAuth.getInstance().getCurrentUser().getUid();
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference uidRef = rootRef.child("AllChatMessages").child(uid);
ValueEventListener valueEventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
for(DataSnapshot ds : dataSnapshot.getChildren()) {
for(DataSnapshot dSnapshot : ds.getChildren()) {
for(DataSnapshot snap : dSnapshot.getChildren()) {
String key = snap.getKey();
Log.d("TAG", key);
}
}
}
}
#Override
public void onCancelled(DatabaseError databaseError) {}
};
uidRef.addListenerForSingleValueEvent(valueEventListener);
The output will be all those ids that you are looking for.
Add and implement a ChildEventListener instead of a ValueEventListener.
Your "somevalue" should be in the DataSnapshot of the overriden onChildChanged method.
I have write up a code glimpse of it is in below code. What I was doing was getting value from the node of users. I have retracted all the children of it by the below code you may also try the same way maybe it would help you.
mFirebaseUserReference = FirebaseDatabase.getInstance().getReference();
userReference = mFirebaseUserReference.child("Users");
childEventListener = new ChildEventListener() {
#Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
Log.d("Values",dataSnapshot+"");
HashMap temp = (HashMap) dataSnapshot.getValue();
if (temp!=null){
if (!temp.get("id").equals(FirebaseAuth.getInstance().getCurrentUser().getUid())){
SignInModel signInModel = new SignInModel();
signInModel.setPhotoUrl((String)temp.get("photoUrl"));
signInModel.setEmail((String)temp.get("email"));
signInModel.setName((String)temp.get("name"));
signInModel.setId((String)temp.get("id"));
arrayList.add(signInModel);
adapter.notifyDataSetChanged();
}
}
}
#Override
public void onChildChanged(DataSnapshot dataSnapshot, String s) {
}
#Override
public void onChildRemoved(DataSnapshot dataSnapshot) {
}
#Override
public void onChildMoved(DataSnapshot dataSnapshot, String s) {
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
};
userReference.addChildEventListener(childEventListener);
Hope that helps.

How to get list of root firebase database

I'm trying to get a list of one of my root nodes of my database
my database is set up like this
beans-card
--user
--008675
--...
--...
--...
--007865
--...
--...
--...
and so on...
i'm trying to get a list of the user which is made up of 6 digit string.
my code to read is
DatabaseReference list_db = FirebaseDatabase.getInstance().getReference();
list_db.addValueEventListener(new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
getAllTask(dataSnapshot);
}
#Override
public void onCancelled(DatabaseError databaseError) {
}
});
private void getAllTask (DataSnapshot dataSnapshot) {
for (DataSnapshot singleSnapshot : dataSnapshot.getChildren()) {
Users users = singleSnapshot.getValue(Users.class);
allUsers.add(users);
}
recyclerViewAdapter = new RecyclerViewAdapter(this,
allUsers);
recyclerView.setAdapter(recyclerViewAdapter);
}
and the error im currently getting is
11-28 13:44:38.622 23572-23572/ca.mobile.jenovaprojects.rewardsreader W/ClassMapper: No setter/field for 778018 found on class ca.mobile.jenovaprojects.rewardsreader.main.models.Users
for each user thats in the database.
thanks for any insight
To get those user 6 digit ids into a list, please use the following code:
DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference userRef = rootRef.child("user");
ValueEventListener eventListener = new ValueEventListener() {
#Override
public void onDataChange(DataSnapshot dataSnapshot) {
List<String> list = new ArrayList<>();
for(DataSnapshot ds : dataSnapshot.getChildren()) {
String userId = ds.getKey();
list.add(userId);
}
Log.d("TAG", list);
}
#Override
public void onCancelled(DatabaseError databaseError) {}
};
userRef.addListenerForSingleValueEvent(eventListener);
Now the list contains: 008675, 007865 and so on.

Categories