如何在Firebase Android中维护用户的状态



我正在开发一个聊天应用程序,我必须在其中维护用户的在线状态,并且我正在使用的技术是Firebase,所以我该怎么做才能得到任何形式的帮助。 提前感谢...

Mabz 在概念上的想法是正确的,但我想强调一下 Firebase 的一个专门针对您的用例的功能。

我遇到的麻烦是将实时数据库更新为"离线"状态。也就是说,如果客户端(例如您的Android应用程序)处于离线状态,它应该如何告诉数据库?

解决方案:使用DatabaseRef.onDisconnect()自动设置离线状态

DatabaseRef presenceRef = 
FirebaseDatabase.getInstance().getReference("disconnectmessage");
// Write a string when this client loses connection
presenceRef.onDisconnect().setValue("I disconnected!");

从文档中:

当您建立 onDisconnect() 操作时,该操作将继续存在 Firebase 实时数据库服务器。服务器检查安全性 确保用户可以执行请求的写入事件,并通知 您的应用(如果无效)。然后,服务器监视 连接。如果在任何时候连接超时或处于活动状态 由实时数据库客户端关闭,服务器检查安全性 第二次(以确保操作仍然有效),然后 调用事件。

一个(稍微)更实际的示例可能会在应用首次连接时执行以下操作:

DatabaseRef userStatus = 
FirebaseDatabase.getInstance().getReference("users/<user_id>/status");
userStatus.onDisconnect.setValue("offline");
userStatus.setValue("online");

注意:请注意最后两个"联机"和"脱机"状态行的顺序。不要交换它,否则您可能会有"幽灵用户",以防 onDisconnect 处理程序由于断开连接本身而无法注册。(这实际上是一个竞争条件问题)

根据您提供的信息,不考虑性能或带宽限制,以下是我如何解决此问题的方法:

在实时数据库中使用服务和线程:

在实时数据库中,我将有一个 OnlineStatus 线程,然后我将保存用户 ID 的子键值对,并将其值设置为"绿色"或"黄色"或"红色";这将为我提供用户是在线还是离开的状态。所以这看起来像:

在线状态

  • 用户 1:绿色
  • 用户 2:黄色
  • 用户 3:红色

创建一个服务,用于检查:

  • 用户已通过身份验证
  • 该应用程序在后台运行

如果用户已通过身份验证并且应用已打开,则作为键写入 OnlineStatus 线程"当前用户",将"绿色"作为值写入。

如果应用在后台运行并且用户已通过身份验证,则执行相同的操作,但"黄色"是值。

其他任何东西都应该产生"红色"。另请注意,如果用户注销,您可能希望在该操作期间写入"红色"。

因此,这允许每个设备更新Firebase实时数据库。剩下的就是添加对 OnlineStatus 位置的引用,以通过 ValueEventListener 侦听更改。

希望这有帮助。

可以使用数据库引用侦听器".info/connected"加上断开连接方法dbRef.onDisconnect()来解决在线用户的存在问题。

下面是一些示例代码:

onlineStatus = db.getReference("users/"+user.getUid()+"/onlineStatus");
connectedRef = FirebaseDatabase.getInstance().getReference(".info/connected");
connectedRef.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot snapshot) {
boolean connected = snapshot.getValue(Boolean.class);
if (connected) {
onlineStatus.onDisconnect().setValue("offline");
onlineStatus.setValue("Online");
} else {
onlineStatus.setValue("offline");
}
}
@Override
public void onCancelled(@NonNull DatabaseError error) {
}
});

您可以在我的网站上阅读本文的更多信息。

最新更新