使用随机生成的密钥

时间:2017-08-13 20:48:07

标签: android firebase firebase-realtime-database

我正在尝试创建一个基本应用,我将消息发送到Firebase中的实时数据库并在列表视图中接收它们。(这是Whatsapp的翻版。)我发送用户的用户名和消息通过推送消息到数据库。但是,由于随机生成的密钥,我无法读取它们并从中创建列表视图。 有没有办法接收参考聊天的所有孩子并将它们放在列表视图中?

PS。我无法使用.getKey函数,因为消息将来自不同的设备。

PPS。 可以>提供额外的代码或详细信息。

代码:

public class MessageBoard extends AppCompatActivity {
    private static final String TAG = "MessageBoard";

    private FirebaseAuth mAuth= FirebaseAuth.getInstance();
    private FirebaseDatabase database = FirebaseDatabase.getInstance();
    private FirebaseUser user = mAuth.getCurrentUser();
    private ArrayList<String> chatlist;
    private ArrayAdapter<String> arrayAdapter;
    private DatabaseReference ref;
    private DatabaseReference Users;
    private String username;
    private String email;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_message_board);

        final Button SignOut = (Button) findViewById(R.id.SignOut);
        final Button SendMessage = (Button) findViewById(R.id.SendMessage);
        final EditText MessageText = (EditText) findViewById(R.id.Message_Text);
        final ListView listView = (ListView) findViewById(R.id.Listview);
        final TextView UserNameDis = (TextView) findViewById(R.id.UserNameDisplay);
        if(user != null){
            email = user.getEmail();

        }


        chatlist = new ArrayList<String>();

        arrayAdapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, chatlist);

        listView.setAdapter(arrayAdapter);

        ref = database.getReference("chat");

//-----------------------------------------------------------------------------------------------------------------------------------------
//to login screen

        if(user == null){
            startActivity(new Intent(MessageBoard.this, Login.class));
            Log.d(TAG, "Login");
        }else{
            Toast.makeText(MessageBoard.this, "Login Succesfull.",
                    Toast.LENGTH_SHORT).show();
        }




//-----------------------------------------------------------------------------------------------------------------------------------------
//to username screen
        if(user.getDisplayName() == null){
            startActivity(new Intent(MessageBoard.this, Username.class));
            Log.d(TAG, "Username");
        }else{
            Toast.makeText(MessageBoard.this, "Username Known.",
                    Toast.LENGTH_SHORT).show();
        }



//-----------------------------------------------------------------------------------------------------------------------------------------
        //set username welcome text
        username = user.getDisplayName();
        String Welcome = "Welcome " + username;
        UserNameDis.setText(Welcome);


//-----------------------------------------------------------------------------------------------------------------------------------------
//sign out button
        SignOut.setOnClickListener(new View.OnClickListener() {
            public void onClick(View v) {
                FirebaseAuth.getInstance().signOut();
                startActivity(new Intent(MessageBoard.this,Login.class));

            }
        });



//-----------------------------------------------------------------------------------------------------------------------------------------
// chat data update
        ref.orderByKey();

        ref.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                //where I think the receiving code should be
            }

            @Override
            public void onCancelled(DatabaseError databaseError) {

            }
        });
//-----------------------------------------------------------------------------------------------------------------------------------------
//message send
        SendMessage.setOnClickListener(new View.OnClickListener(){
            public void onClick(View v) {
                String push = ref.push().getKey();
                ref.child(push).child("message").setValue(username);
                ref.child(push).child("username").setValue(username);

            }
        });
//-----------------------------------------------------------------------------------------------------------------------------------------
    }

}

2 个答案:

答案 0 :(得分:0)

从节点中检索数据,您可以获取每个随机生成的密钥及其值。

ref.addValueEventListener(new ValueEventListener()
{
@Override
public void onDataChange(DataSnapshot dataSnapshot)
{
    HashMap<String, Object> allMessage = (HashMap<String, Object>) 
    dataSnapshot.getValue();
    String[] pushIds = allMessage.keySet().toArray(new String[0]);
    for (int j = 0; j < allMessage.size(); j++)
    {
        HashMap<String, Object> singleMessage = (HashMap) 
        allMessage.get(pushIds[j]);
        Message message = new message(singleMessage);
        allRequests.add(message);

    }
}

@Override
public void onCancelled(DatabaseError databaseError)
{

}
});

您的模型类

 public class Message
 {
    String message;
    public Message(HashMap<String,Object> singleMessage)
  {
    message = singleMessage.get("message").toString();
  }
  };

答案 1 :(得分:0)

我没有看到你说你想要根据随机生成的密钥订购的任何逻辑(意思是,你对这些密钥一无所知)。你为什么要这样做?您可以使用email_id或device_id作为密钥,以便跟踪特定节点。这节省了大量互联网络带宽,因为只有在特定节点发生变化时才会发生PUSH。

在您的情况下,方法是更好的解决方案:

1)你不随机生成密钥;您可以使用device_id,它是唯一的固定值作为键。这样每个客户端都可以跟踪特定节点。 - 这是最好的方法。

2)如果必须随机生成密钥,则可以将Map<ID, MSG_TEXT>放入JSON消息数组对象(节点)中。但是,问题是,这里的每个设备都必须监听Json Message Array节点。如果有数百万设备R / W发生,这意味着,有不必要的消息可以到您的设备,因为根据firebase的数据快照定义,JSON消息数组内的任何内容都会发生变化,PUSH就会发生。

如果你的设备数量有限(100或更少),那就没关系了。在这种情况下,任何设备都可以使用setValue("Map<Random_key, msg>")来增加价值。每条新消息都会获得新索引(例如第一条消息有0,第二条消息等等)。所以,你可以按索引订购。

您可以在Firebase节点中编写哪些值,请参阅以下链接:https://firebase.google.com/docs/database/android/read-and-write