我首先尝试在数据库中实例化每个用户,如下所示:
emails : {
email: "jerry@gmail.com" {
uid: "x"
}
}
我很快发现我无法存储电子邮件,因为它有@
和.
。我本来打算像用户那样查看用户:
func userLookUpByEmail (email: String) -> String {
var userID: String = "nil"
ref.queryOrderedByChild("emails").queryEqualToValue(email).observeSingleEventOfType(.ChildAdded, withBlock: { snapshot in
if snapshot.value != nil {
print(snapshot.value)
userID = snapshot.value as! String
}
else {
print ("user not found")
userID = "nil"
}
})
return userID
}
然而,我意识到这是行不通的。从提供电子邮件接收UID的有效方法是什么?
答案 0 :(得分:5)
回答您的问题,因为您无法将电子邮件作为子密钥,您可以执行其他操作,将uid设置为密钥,将电子邮件设置为子项。
emails : {
uid: {
email: "jerry@gmail.com"
}
}
然后你的代码会有所改变。
func userLookUpByEmail (email: String, completionHandler: (result: String) -> Void) {
var userID: String = "nil"
ref.child("emails").queryOrderedByChild("email").queryEqualToValue(email).observeSingleEventOfType(.ChildAdded, withBlock: { snapshot in
if snapshot.value != nil {
print(snapshot.key)
userID = snapshot.key as! String
}
else {
print ("user not found")
userID = "nil"
}
completionHandler(userID)
})
}
致电userLookUpByEmail
:
userLookUpByEmail(email) {
(result: String) in
print("\(result)")
}
另一方面,我想知道为什么你的数据库中有一个emails
分支,因为你可以拥有一个users
分支(如果你还没有)并存储任何用户数据在那里,包括电子邮件。这将使您的数据结构更加干净和可靠。再次,我在这里想,因为我不确切地知道你的需求。
users : {
uid: {
email: "jerry@gmail.com",
name: "Jerry Maguire",
...
}
}
答案 1 :(得分:3)
首先,您无法在数据库中存储某些字符。根据Firebase文档,(https://firebase.google.com/docs/database/ios/structure-data)
如果您创建自己的密钥,它们必须是UTF-8编码,最多可以是768字节,并且不能包含。,$,#,[,],/或ASCII控制字符0-31或127
然而,正如你所看到的," @"符号不是其中之一。对于点,您可以使用一个用另一个字符替换点的函数。例如,"•"。这是一个例子:
func createNewEmail(oldEmail: String) -> String{
return oldEmail.componentsSeparatedByString(".").joinWithSeparator("•")
}
它的作用是将电子邮件拆分为" email @ example"和" com"。然后,它重新加入他们与新角色,创建"电子邮件@ example•com"
如果你需要旧的电子邮件,你可以反过来做同样的事情。
func getOldEmail(newEmail: String) -> String{
return newEmail.componentsSeparatedByString("•").joinWithSeparator(".")
}
然后你可以像这样格式化你的树
emails:
email@example•com: UID123456789
最后,对于您的原始问题,该函数可以像这样编写
func userLookUpByEmail (email: String) -> String {
let newEmail = createNewEmail(email)
var userID: String = "nil"
ref.child("emails").child(newEmail).observeSingleEventOfType(.ChildAdded, withBlock: { snapshot in
if snapshot.value != nil {
print(snapshot.value)
userID = snapshot.value as! String
}
else {
print ("user not found")
userID = "nil"
}
})
return userID
}
然而,你可能会得到" nil"每次。这是因为observeSingleEventOfType是一个闭包。这意味着它在您的应用程序的后台运行。因此,userID可能会在闭包内更改之前返回。您可能希望基于闭包内的userID运行任何代码,而不是返回userID。例如,而不是这样做:
func userLookUpByEmail (email: String) -> String {
let newEmail = createNewEmail(email)
var userID: String = "nil"
ref.child("emails").child(newEmail).observeSingleEventOfType(.ChildAdded, withBlock: { snapshot in
if snapshot.value != nil {
print(snapshot.value)
userID = snapshot.value as! String
}
else {
print ("user not found")
userID = "nil"
}
})
return userID
}
doSomethingWith(lookUserUpByEmail(email@example.com))
你可以这样做:
func userLookUpByEmail (email: String){
let newEmail = createNewEmail(email)
var userID: String = "nil"
ref.child("emails").child(newEmail).observeSingleEventOfType(.ChildAdded, withBlock: { snapshot in
if snapshot.value != nil {
print(snapshot.value)
userID = snapshot.value as! String
doSomethingWith(userID)
}
else {
print ("user not found")
userID = "nil"
doSomethingWith(userID)
}
})
}