Я пытаюсь проверить свою базу данных Firebase, чтобы узнать, есть ли уже имя пользователя в базе данных. К сожалению, когда я использую уже сохраненное имя пользователя, он не сообщает мне об этом. Код ниже.
@objc func pushedToRegister(_ sender: SignInSignUpButtons) {
checkUserNameAlreadyExist()
Auth.auth().createUser(withEmail: email.text!, password: password.text!, completion: { (user, error) in
if error != nil {
self.errorMessage = (error?.localizedDescription)!
print(error!)
self.showErrorView(forReason: 0)
return
}
else {
print("Registration was successful!")
//Here we should go back to the home screen where the message at the top should say welcome back USER!
if let userID = user?.user.uid {
//Create User Profile
let databaseRef = Database.database().reference()
let usersRef = databaseRef.child("Users").child(userID)
let usernameValue = ["username":self.username.text]
usersRef.updateChildValues(usernameValue, withCompletionBlock: { (err, ref) in
if err != nil {
print(err!.localizedDescription)
self.showErrorView(forReason: 2)
return
}
//Profile created and updated!
self.navigationController?.popViewController(animated: true)
})
}
}
})
}
func checkUserNameAlreadyExist() {
let ref = Database.database().reference()
var usernameTaken = false
ref.child("Users").queryOrdered(byChild: "username").queryEqual(toValue: username.text!).observeSingleEvent(of: .value, with: { snapshot in
if snapshot.exists(){
usernameTaken = true
print("username taken")
}else{
usernameTaken = false
print("username available")
}
}) { error in
print(error.localizedDescription)
}
if usernameTaken == false{
//do stuff with unique username
}
}
К сожалению, каждый раз, когда я ввожу одно и то же имя пользователя, это позволяет мне каждый раз создавать новый профиль. Это не предупреждает меня о том, что имя пользователя уже занято.
Функции Firebase асинхронны, поэтому они не блокируют выполнение остальной части кода. Если вы хотите, чтобы ваш код ждал завершения функции, можно использовать замыкания. Вы можете ознакомиться с моим Сообщение блога о закрытии, чтобы увидеть некоторые примеры.
Кроме того, показанный код на самом деле ничего не делает, чтобы предотвратить выполнение остальной части функции. Вам нужно написать какое-то условие, чтобы справиться с этим. Например, вы можете использовать логическое значение в обработчике завершения, например:
func checkUserNameAlreadyExist(completion: @escaping (Bool) -> Void) {
let ref = Database.database().reference()
ref.child("Users").queryOrdered(byChild: "username").queryEqual(toValue: username.text!).observeSingleEvent(of: .value, with: { snapshot in
if snapshot.exists() {
usernameTaken = true
print("username taken")
completion(true)
} else {
usernameTaken = false
print("username available")
completion(false)
}
}) { error in
print(error.localizedDescription)
completion(true)
}
}
Затем в pushToRegister
вы проверяете, истинно ли логическое значение, прежде чем продолжить.
@objc func pushedToRegister(_ sender: SignInSignUpButtons) {
checkUserNameAlreadyExist() { isTaken in
if (isTaken == true) {
// show some message to the user
return
}
Auth.auth().createUser(withEmail: email.text!, password: password.text!, completion: { (user, error) in
if let error = error {
self.errorMessage = error.localizedDescription
print(error)
self.showErrorView(forReason: 0)
return
}
print("Registration was successful!")
//Here we should go back to the home screen where the message at the top should say welcome back USER!
if let userID = user?.user.uid {
//Create User Profile
let databaseRef = Database.database().reference()
let usersRef = databaseRef.child("Users").child(userID)
let usernameValue = ["username":self.username.text]
usersRef.updateChildValues(usernameValue, withCompletionBlock: { (err, ref) in
if let err = err {
print(err.localizedDescription)
self.showErrorView(forReason: 2)
return
}
//Profile created and updated!
self.navigationController?.popViewController(animated: true)
})
}
})
}
}
Спасибо, это действительно хорошо работает. Однако это может показаться глупым вопросом ... но почему база данных обновляется каждый раз, когда вы останавливаете запуск приложения, а затем запускаете его снова? Например, если я запускаю приложение, войдите в систему с именем пользователя «Боб», затем попытайтесь зарегистрироваться снова (с помощью «Боб»), появится сообщение «имя пользователя занято». Если я остановлю работу приложения, а затем запущу его снова, я снова смогу зарегистрироваться как «Боб».
Вы видите в консоли надпись «имя пользователя доступно»? С вашим кодом прямо сейчас он будет создавать нового пользователя каждый раз, вам нужно написать условие для оператора Auth.auth (). CreateUser.