Reputation: 1274
I'm trying to receive data from database in other value listener.
class MyFragment : Fragment() {
private lateinit var reference: DatabaseReference
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
reference = FirebaseDatabase.getInstance().reference.child("FIRST_ROOT")
.child("FIRST_CHILD")
.child("CHILD_1")
}
override fun onActivityCreated(savedInstanceState: Bundle?) {
super.onActivityCreated(savedInstanceState)
reference.addValueEventListener(object : EventListener() {
override fun onDataChange(p0: DataSnapshot?) {
val childOfSecondRoot= p0?.value
FirebaseDatabase.getInstance().reference.child("SECOND_ROOT")
.child(childOfSecondRoot).addListenerForSingleValueEvent(object : EventListener() {
override fun onDataChange(p0: DataSnapshot?) {
doingMyJob(p0?.value)
}
})
}
})
}
My goal is to run method doingMyJob
once per change in observed value in reference.
For some reason event listener added as addListenerForSingleValueEvent
is calling method doMyJob
one more time for each time reference
trigger instead of run it only once per change. First read from reference
is OK, but second call doMyJob
2 times, third 3 times and so on. After restart app history starts from beginning. Method doMyJob()
don't change any values in database.
For now I know that parent listener is called incrementaly for each single change in observed value.
Database structure:
|MAIN_ROOT
|\FIRST_ROOT
| \FIRST_CHILD
| |DATA_TO_RECEIVED //reference field - parent listener for many events
|\SECOND_ROOT
| \DATA_TO_RECEIVED // root name received in nested listener-as single value
| |CHILD_1
| |CHILD_2
| |CHILD_3
Am I doing something wrong? Is there a possibility to run listener from listener avoiding incremental call of nested listener?
PS: Sorry for ugly code. I was trying to simplyfy problem as much as it was possible.
Upvotes: 3
Views: 3084
Reputation: 1274
Funny thing. Method doMyJob
after show dialog launch new fragment (sorry for missed it in my question) and after I close it fragment which add listener in onActivityCreated is relaunched so... val reference
is assigned again and another listerer is added.
I just love this kind of bugs. Thanks everybody for help.
Upvotes: 1
Reputation: 12005
you're using a singleEventListener
in your second query, but in your first you're still using a normal event listener that won't go away automatically. So that might be the reason why your code gets called multiple times. So the problem is not that you're single event listener is being called multiple times, but the one above might be and everytime it creates a new single event listener which in turn call your method multiple times.
reference.addValueEventListener(object : EventListener() { //ordinary event listener will be kept running
override fun onDataChange(p0: DataSnapshot?) {
val childOfSecondRoot= p0?.value
FirebaseDatabase.getInstance().reference.child("SECOND_ROOT")
.child(childOfSecondRoot).addListenerForSingleValueEvent(object : EventListener() {
override fun onDataChange(p0: DataSnapshot?) {
doingMyJob(p0?.value)
}
})
}
})
Upvotes: 2