我使用Firebase进行注册流程。当我检查数据库中是否已存在电子邮件时,如下所示:
refUsers.queryOrdered(byChild: "email").queryEqual(toValue: emailText).observeSingleEvent(of: .value, with: { snapshot in
if (snapshot.value is NSNull) {
print("Unique email")
// Move to Password View.
let passwordViewController = self.storyboard?.instantiateViewController(withIdentifier: "PasswordViewController") as! PasswordViewController
self.navigationController?.present(passwordViewController, animated: true, completion: nil)
// Pass the emailText to the last View of the flow.
self.singleton.sharedInstance.emailText = emailText!
}
else {
print("Duplicate email")
}
})
问题是,我没有权限查看数据库中的/用户因为我的规则是:
{
"rules": {
".read": "auth != null",
".write": "auth != null"
}
}
我知道我可以使用Auth.auth().createUser
查找电子邮件是否重复,但这不仅仅是我在注册流程中检查的电子邮件。我也使用相同的方法来获取唯一的用户名。我怎样才能做到这一点?
答案 0 :(得分:3)
正如您所看到的,这不是最好的方法。您不应该手动检查电子邮件是否已经存在 - Firebase可以在用户注册时为您执行此操作,为什么您不想使用它?
您需要的是一种不同的方法。我现在可以想到两种方式:
首先:
您可以向Firebase添加新规则,例如:
"rules": {
"usernames": {
".read": true,
".write": "auth != null"
},
"emails": {
".read": true,
".write": "auth != null"
}
}
}
您在此处创建一个名为usernames
的新节点,每个用户都可以访问和读取该节点。
在这里,您应该拥有注册用户拥有的所有用户名的副本,并在注册时检查用户的用户名是否已经在此节点内。
第二种方式:
您可以稍微修改注册流程,让用户在没有用户名的情况下注册。创建帐户后,您可以设置用户名。有了一个很好的流程,它看起来都是相同的注册形式。
<强>更新强>
使用上述规则,用户应该能够在不注册的情况下从emails
和usernames
进行阅读。这样您就可以获取数据并比较电子邮件或用户名是否已被使用。
只需确保在用户注册时将您的电子邮件和用户名插入这两个节点。
答案 1 :(得分:0)
虽然@ZassX的回答帮助了我,但我已经了解了对于那些像我这样困惑的人来说,这是一个很好的方法。
最好的方法是在/users
"auth != null"
规则下保护用户数据安全。仅向所有人显示用户的元数据,其中仅包含每个用户的电子邮件和密码。例如:
<强>数据库强>
{
“metaData”: {
uid: {
“email”: …,
“password”: …
}
},
“users”: {
uid: {
“email”: …,
“password”: …
// other information
}
}
}
安全强>
{
"rules": {
“metaData”: {
“.read”: true,
“.write”: “auth !== null”
},
“users”: {
“.read”: “auth !== null”,
“.write”: “auth !== null”
}
}
}
现在可以匹配metaData中的信息,而无需先对用户进行身份验证。当然,随着您添加更多安全性,这会变得更加复杂,但为了便于理解,就是这样。