Android

Checking if a particular value exists in the Firebase database

Проверка наличия определенного значения в базе данных Firebase

Я создаю приложение для Android с использованием Firebase базы данных реального времени. Когда новый пользователь регистрируется в моем приложении, данные этого пользователя сохраняются в базе данных Firebase.

Для регистрации пользователь должен предоставить следующие данные:


  1. Полное имя

  2. Электронная почта

  3. Имя пользователя

  4. Пароль

Структура базы данных

введите описание изображения здесь

Всякий раз, когда новый пользователь пытается зарегистрироваться, я должен убедиться, что имя пользователя каждого пользователя уникально, поэтому я проверяю базу данных, username введенное пользователем, уже существует в базе данных или нет.

Для этого я написал следующий метод:

private boolean usernameExists(String username) {
DatabaseReference fdbRefer = FirebaseDatabase.getInstance().getReference("Users/"+username);
return (fdbRefer != null);
}

Моя логика, лежащая в основе этого метода, заключается в том, что если getReference метод не может найти ссылку на указанный путь, он вернет null, чтобы я мог вернуть, есть fdbRefer это null или нет. Если fdbRefer есть null, то это означает, что username не существует в базе данных.

Проблема

Проблема с этим методом заключается в том, что он всегда возвращает, true независимо от того, существует ли введенное username значение в базе данных или нет. Что привело меня к мысли, что fdbRefer никогдаnull.

Это подводит меня к моему вопросу...

Вопрос

Что возвращает getReference метод, когда он не может найти указанный путь в firebase базе данных, и каков правильный способ проверить, существует ли username уже в базе данных или нет?

Переведено автоматически
Ответ 1

Чтобы проверить существование пользователя, пожалуйста, используйте приведенный ниже код:

DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
DatabaseReference userNameRef = rootRef.child("Users").child("Nick123");
ValueEventListener eventListener = new ValueEventListener() {
@Override
public void onDataChange(DataSnapshot dataSnapshot) {
if(!dataSnapshot.exists()) {
//create new user
}
}

@Override
public void onCancelled(DatabaseError databaseError) {
Log.d(TAG, databaseError.getMessage()); //Don't ignore errors!
}
};
userNameRef.addListenerForSingleValueEvent(eventListener);

Вы также можете использовать запрос для достижения того же, что и этот:

DatabaseReference rootRef = FirebaseDatabase.getInstance().getReference();
Query query = rootRef.child("Users").orderByChild("userName").equalTo("Nick123");
query.addValueEventListener(/* ... */);

Это еще один подход, который проходит через весь Users узел, но не использует просто прямую ссылку на одного пользователя. Эта опция, скорее всего, будет использоваться, когда вы используете в качестве уникального идентификатора для пользователей uid вместо имени пользователя (как вы делаете прямо сейчас). Итак, если структура вашей базы данных может выглядеть примерно так:

Firebase-root
|
--- Users
|
--- uid
|
--- userName: "Test User"
|
--- emailAddress: "user@email.com"

Рекомендуется второе решение.

Существует также другое решение, которое предполагает создание другого узла с именем userNames, в котором вы можете хранить только уникальные имена пользователей. Пожалуйста, также ознакомьтесь ниже с соответствующими правилами безопасности:

"Users": {
"$uid": {
".write": "auth !== null && auth.uid === $uid",
".read": "auth !== null && auth.provider === 'password'",
"userName": {
".validate": "
!root.child('userNames').child(newData.val()).exists() ||
root.child('userNames').child(newData.val()).val() == $uid"

}
}
}

Но поскольку в этом случае ваше имя пользователя уже является именем узла, я рекомендую вам перейти к первому.

Ответ 2

Попробуйте это:

DatabaseReference ref=FirebaseDatabase.getInstance().getReference().child("Users");
ref.orderByChild("username").equalTo(Nick123).addValueEventListener(new ValueEventListener(){
@Override
public void onDataChange(DataSnapshot dataSnapshot){
if(dataSnapshot.exist() {
//username exist
}
}

Вы должны использовать orderbychild и equalto, чтобы проверить значение, если оно там есть.
Если вы не используете orderbychild и equalto, то он просто проверит, существует ли username дочерний узел, и значение его не волнует.

это orderByChild("username").equalTo(Nick123) все равно что сказать:

WHERE username=Nick123
Ответ 3

У меня отлично работает

DatabaseReference reference = FirebaseDatabase.getInstance().getReference();
Query query = reference
.child(getString(R.string.dbname_users))
.orderByChild("username")
.equalTo(username);
query.addListenerForSingleValueEvent(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
if(dataSnapshot.getChildrenCount()>0) {
//username found

}else{
// username not found
}

}
@Override
public void onCancelled(DatabaseError databaseError) {

}
});
Ответ 4

Вместо проверки существования ссылки вы можете использовать запрос OrderBy, чтобы проверить, существует ли уже username

Запрос orderByChild('username').equalTo(username) вернет данные, если некоторые данные уже существуют, в противном случае он вернет null.

java android firebase firebase-realtime-database