将数据插入Firebase -Android-并检查特定属性 [英] Insert data to firebase -Android - and check specific properties
问题描述
我需要将课程对象插入到Firebase中,因此我将代码的onData更改部分放在此处. 首先,我获得了数据快照并插入了我在firebase中获得的课程,之后,我扫描了课程列表并检查: 如果日期和时间存在在任何课程的Firebase中,则我要执行其他操作,将课程对象插入firebase中. 主要问题是: 当我插入课程的详细信息并按添加时,该课程至少要两次输入Firebase,如果尝试再次插入,则程序将进入无限循环. 会很高兴为您提供帮助!
I need to insert lesson object to firebase, so I put here the onData change section of code. First of all I get data snapshot and insert the lessons that I have in firebase, after that I scan the List of Lessons and check: if the date and time exist in the firebase in any Lesson so I do something else I insert the lesson object to firebase . The main problem is : when I insert the details of the lesson and press add, the lesson enter to the firebase twice minimum, and if I try another insertion the program enter to infinite loop . will be happy for any help !
ArrayList<Lesson> existLesson=new ArrayList<>();
List<String> keys = new ArrayList<>();
int counter=0;
public void getLessons(DataSnapshot dataSnapshot){
//insert the lessons to "existLesson" arrayList
for (DataSnapshot keyNode : dataSnapshot.getChildren()) {
keys.add(keyNode.getKey());
Lesson lesson = keyNode.getValue(Lesson.class);
existLesson.add(lesson);
Log.i(tag, "data : " + lesson.getSubject());
}//for
}
int flag=1;
@Override
public void addLesson(final String subject, final String topic, final String date, final String time) {
mDatabase.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
getLessons(dataSnapshot);
//Check if date and time is busy
for (Lesson lessonToCheck : existLesson) {
if (lessonToCheck.getDate().equals(date) && lessonToCheck.getTime().equals(time)) {
flag = 0;
} else {
flag = 1;
}
}//for
if (flag == 0) {
Toast.makeText(LessonDetails.this, "date exist", Toast.LENGTH_SHORT).show();
// Check empty lessons
nearestLessons(existLesson, date, time);
} else {
if (flag == 1) {
String id = mDatabase.push().getKey();
Lesson lesson = new Lesson(subject, topic, date, time, id); //create lesson
Toast.makeText(LessonDetails.this,
subject + " - " + topic + " - " + date + " - " + time, Toast.LENGTH_SHORT).show();
mDatabase.child(id).setValue(lesson);
} //add lesson to DB
} //else
Log.i(tag,"end");
} //onDataChange
推荐答案
调用you're adding a listener to the data at
时.该侦听器将立即读取数据并调用您的onDataChange
,然后继续侦听数据更新.
When you call you're adding a listener to the data at
. This listener will immediately read the data and call your onDataChange
, and then continues to listen for updates to the data.
对于数据的每次更新,它都会再次调用您的onDataChange
.并且由于您正在更新onDataChange
中的数据,因此以setValue
-> onDataChange
-> setValue
-> onDataChange
->> ...
For each update to the data, it calls your onDataChange
again. And since you're updating the data inside onDataChange
, this ends in an endless loop of setValue
->onDataChange
->setValue
->onDataChange
->...
要解决此问题,通常应使用addListenerForSingleValueEvent
,因为它只会获取一次值,并且不会继续监听更改.
To fix this, you'd typically use addListenerForSingleValueEvent
instead, as this only gets the value once and doesn't continue listening for changes.
所以像这样:
mDatabase.addForListenerValueEvent(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
getLessons(dataSnapshot);
//Check if date and time is busy
for (Lesson lessonToCheck : existLesson) {
if (lessonToCheck.getDate().equals(date) && lessonToCheck.getTime().equals(time)) {
flag = 0;
} else {
flag = 1;
}
}//for
if (flag == 0) {
Toast.makeText(LessonDetails.this, "date exist", Toast.LENGTH_SHORT).show();
// Check empty lessons
nearestLessons(existLesson, date, time);
} else {
if (flag == 1) {
String id = mDatabase.push().getKey();
Lesson lesson = new Lesson(subject, topic, date, time, id); //create lesson
Toast.makeText(LessonDetails.this,
subject + " - " + topic + " - " + date + " - " + time, Toast.LENGTH_SHORT).show();
mDatabase.child(id).setValue(lesson);
} //add lesson to DB
} //else
Log.i(tag,"end");
} //onDataChange
})
请注意,由于您是根据数据的当前值更新数据,因此有可能另一个用户几乎同时执行相同的操作.如果这可能导致用例中的更新冲突,请考虑使用事务,它将对代码的读取和写入合并为一个(可重复的)操作.
Note that, since you're updating the data based on its current value, there's a chance that another user may be doing the same operation at almost the same time. If this can lead to conflicting updates in your use-case, consider using a transaction which combines the read and write from your code into a single (repeatable) operation.
这篇关于将数据插入Firebase -Android-并检查特定属性的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!