我将Firebase添加到我的网站并创建了一个注册表单。 当用户点击"注册"按钮,它使用" Firebase身份验证"创建用户,然后更新用户的displayName,最后将有关用户的一些数据添加到数据库:
firebase.auth().createUserWithEmailAndPassword(email, password).then(function () {
profile = firebase.auth().currentUser;
profile.updateProfile({
displayName: "name-value"
}).then(function() {
// Update successful.
firebase.database().ref("/users/" + profile.uid).set({
data:{
country: "country-value",
city: "city-value"
}
});
});
}).catch(function(error) {
// Handle Errors here.
});
在我更改数据库规则之前,一切正常:
{
"rules": {
".read": true,
".write": true
}
}
}
要:
{
"rules": {
"users": {
".read": true,
"$user": {
".write": "auth.token.name !== null"
}
}
}
}
我使用 auth.token.name ,因为它是在guide中写的,用于检查用户的displayName是否存在(我打算让它进行更多检查)以后的事情)。 某种方式"火力基地规则" '认为' auth.token.name 等于null,即使我之前设置了displayName。为什么会发生这种情况,我该怎么做才能使它发挥作用?
提前致谢:)
答案 0 :(得分:3)
首先,Firestore取代了实时数据库,应该用于所有项目 - 更多功能。
重新实时数据库规则,最佳做法是检查uid
变量与显示名称。见Variables:
{
"rules": {
".read": true,
"$comment": {
".write": "!data.exists() && newData.child('user_id').val() == auth.uid"
}
}
}
最后,您使用Firebase身份验证实施数据库安全规则的IIF,您必须使用.onAuthStateChanged
来驱动您的应用,因为您的auth()
变量在初始页面/应用中将会null
一秒钟加载,因为这是一个异步方法。所以,不要尝试在DOM ready
上写或读任何东西。您必须在.onAuthStateChanged
内触发数据库对话,如下所示:
firebase.auth().onAuthStateChanged(function(user) {
if (user) {
//USER SIGNED IN. WE ARE READY
}
else {
//USER IS NOT SIGNED IN
}
});
答案 1 :(得分:0)
我遇到了同样的问题,并找到了更好的解决方案。 Firebase具有一个称为custom claims的功能,用于我们拥有的用例。您想在可从数据库安全规则访问的Firebase匿名身份验证用户上设置一些ID。
该解决方案的高层是制作一个使用admin api设置自定义声明的Cloud Function。您不能从客户端设置自定义声明。
接下来,调用cloud函数更新自定义声明,然后使用Auth.auth().currentUser?.getIDTokenResult(forcingRefresh: true,...
来检索包含自定义声明的更新令牌。此步骤至关重要,因为您需要将自定义声明作为前进的每个请求的一部分发送。
如果有人真的读过这篇文章,我可以输入一个更详细的实现示例。