Comment puis-je verrouiller la base de données Firebase à tout utilisateur à partir d'un domaine (email) spécifique?
j'ai une petite, personnelle Firebase webapp qui utilise la base de données Firebase. Je veux sécuriser (verrouiller) cette application pour n'importe quel utilisateur à partir d'un seul domaine spécifique. Je veux m'authentifier avec Google. Je ne sais pas comment configurer les règles pour dire " seulement les utilisateurs d'un seul domaine spécifique (dire @foobar.com
) peut lire et écrire dans cette base de données".
(une partie du problème que je vois: il est difficile de bootstrap une base de données avec assez d'information pour faire cette utilisation cas de travail. J'ai besoin de connaître de l'utilisateur e-mail au moment de l'authentification, mais auth
l'objet ne contient pas d'e-mail. Il semble que ce soit un problème d'œuf de poule, parce que je dois écrire des règles Firebase qui se réfèrent aux données dans la base de données, mais ces données n'existent pas encore parce que mon utilisateur ne peut pas écrire dans la base de données.)
Si auth
avait l'email, alors je pourrais écrire les règles facilement.
Merci d'avance!
4 réponses
si vous utilisez la nouvelle Firebase c'est maintenant possible, puisque le email
est disponible dans les règles de sécurité.
dans les règles de sécurité Vous pouvez accéder à la fois l'adresse e-mail et si elle est vérifiée, ce qui rend certains grands cas d'utilisation possible. Avec ces règles par exemple, seul un utilisateur gmail authentifié et vérifié peut écrire son profil:
{
"rules": {
".read": "auth != null",
"gmailUsers": {
"$uid": {
".write": "auth.token.email_verified == true &&
auth.token.email.matches(/.*@gmail.com$/)"
}
}
}
}
vous pouvez entrer ces règles dans le Firebase console de Base de données de votre projet.
attention: ne vous fiez pas à cette réponse. Juste ici pour une discussion.
tldr: Je ne pense pas que ce soit possible, sans utiliser votre propre serveur.
Voici ma tentative à ce jour:
{
"rules": {
".read": "auth.provider === 'google' && root.child('users').child(auth.uid).child('email').val().endsWith('@foobar.com')",
".write": "auth.provider === 'google' && root.child('users').child(auth.uid).child('email').val().endsWith('@foobar.com')",
"users": {
"$user_id": {
".write": "auth.provider === 'google' && $user_id === auth.uid && newData.child('email').val().endsWith('@foobar.com')"
}
}
}
}
je crois que ce qui précède dit "seulement permettre aux gens de créer un nouvel utilisateur si ils sont authentifiés par Google, essayez d'écrire dans la base de données du nœud pour eux-mêmes (
cependant, un problème a été signalé: toute le client peut facilement modifier son courriel (en utilisant la console dev) avant que le message ne soit envoyé à Firebase. Nous ne pouvons donc pas faire confiance aux données de l'utilisateur lorsqu'elles sont stockées dans Firebase.
je pense que la seule chose en laquelle nous pouvons avoir confiance est le auth
objet dans les règles. Que auth
l'objet est peuplé par le backend de Firebase. Et, malheureusement, le auth
l'objet n'inclut pas l'adresse email.
Pour la petite histoire, je suis l'insertion de mon utilisateur de cette façon:
function authDataCallback(authData) {
if (authData) {
console.log("User " + authData.uid + " is logged in with " + authData.provider + " and has displayName " + authData.google.displayName);
// save the user's profile into the database so we can list users,
// use them in Security and Firebase Rules, and show profiles
ref.child("users").child(authData.uid).set({
provider: authData.provider,
name: getName(authData),
email: authData.google.email
});
Comme vous pourriez être en mesure d'imaginer, déterminée, l'utilisateur peut remplacer la valeur de email
ici (en utilisant les DevTools, par exemple).
voici le code qui fonctionne très bien avec ma base de données , j'ai établi la règle que seuls les e-mails de ma société peuvent lire et écrire les données de ma base de données firebase .
{
"rules": {
".read": "auth.token.email.matches(/.*@yourcompany.com$/)",
".write": "auth.token.email.matches(/.*@yourcompany.com$/)"
}
}
Code qui fonctionne pour moi.
export class AuthenticationService {
user: Observable<firebase.User>;
constructor(public afAuth: AngularFireAuth) {
this.user = afAuth.authState;
}
login(){
var provider = new firebase.auth.GoogleAuthProvider();
provider.setCustomParameters({'hd': '<your domain>'});
this.afAuth.auth.signInWithPopup(provider)
.then(response => {
let token = response.credential.accessToken;
//Your code. Token is now available.
})
}
}