查询firebase数据库

时间:2018-01-25 22:42:36

标签: java android firebase firebase-realtime-database

我正在使用firebase,并尝试使用firebase函数正确查询数据。从我一直在使用的数据库的许多不同部分查询数据的解决方案,我非常反对并且我真的不确定,只是将单值事件的监听器添加到整个数据库,如下所示: / p>

DatabaseReference myRef = FirebaseDatabase.getInstance().getReference();
myRef.addListenerForSingleValueEvent(...)).

我想要做的是对我正在监听的数据库部分进行适当的查询,并记住那些值事件监听器函数之外的数据,如下所示:

Query lastMessageQuery = myRef.child("chat_messages").child(currChatID).orderByKey().limitToLast(1);
lastMessageQuery.addValueEventListener(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot lastMessageSnapshot) {
        for(DataSnapshot currMessageSnapshot: lastMessageSnapshot.getChildren()) {
            Message lastMessage = currMessageSnapshot.getValue(Message.class);

            if (lastMessage != null) {
                MessageViewBox currMessageView;
                if (isGroup) {
                    currMessageView = new MessageViewBox(
                            lastMessage.getMessage_text(), chatName, chatIcon, lastMessage.getTime_sent(), currChatID, true
                    );
                } else {
                    currMessageView = new MessageViewBox(
                            lastMessage.getMessage_text(), chatName, chatIcon, lastMessage.getTime_sent(), otherUserID, false
                    );
                }
                messageFields.add(currMessageView);
            }
        }
    }

    @Override
    public void onCancelled(DatabaseError databaseError) {

    }
});

Collections.sort(messageFields);
L_MessageListingAdapter messagesAdapter = new L_MessageListingAdapter(
        mView.getContext(), R.layout.a_person_item, messageFields);
mListView.setAdapter(messagesAdapter);

我遇到的问题是,当我想用​​listFields ArrayList填充listview时,列表已经忘记了它的所有元素。

截至目前,我知道有四种可行的解决方案。

  1. 我可以做我最初描述的内容,为我的整个数据库添加一个值事件监听器,转到包含当前聊天的所有消息的快照,然后迭代到最后。显然,这是不可取的,并且可能会出现可怕的扩展

  2. 我可以在数据库的单独部分中保存每个聊天的最后一个消息ID,使用监听整个数据库的方法,然后只有一个值来迭代以获取最后的消息信息为每个聊天。但同样,我不相信这是必要的,因为我概述的查询功能完美无缺。

  3. 我可以致电:

    Collections.sort(messageFields);
    L_MessageListingAdapter messagesAdapter = new L_MessageListingAdapter(
        mView.getContext(), R.layout.a_person_item, messageFields);
        mListView.setAdapter(messagesAdapter);
    
    在将项添加到ArryList之后,在查询函数内部,但是这会为每个聊天重复这段代码,它会重新加载列表以进行我必须经历的尽可能多的聊天,这也是不合需要的,并且我用这种方法遇到的最大问题是它没有解决我遇到的更大问题,这对于这种特殊情况来说不是问题,而是我运行的很多情况成。

  4. [希望]所以这让我想到了我需要解决的最合乎逻辑的问题,即在查询函数之外保持查询数据的问题。

  5. 我几乎肯定(4)是可能的,似乎这是最好的做法,但我只是不确定如何以优雅的方式实现这一目标。我尝试将ArrayList设为private,private static,public和public static。这些都不起作用。

    希望问题很清楚,我感谢任何可以解决这个问题的建议。

1 个答案:

答案 0 :(得分:2)

您无法将Message类的对象添加到messageFields方法中的onDataChange()列表中,并查看此方法外部填充的相同列表。由于onDataChange()方法的异步行为,列表将始终为空。这意味着甚至在从数据库获取数据之前就会调用此方法。因此,快速解决方法是在方法中使用该列表,或者尝试通过阅读此post的答案的最后部分来处理此异步方法。