I need to create a validation rule in firebase to don't have repeated data like a primary key in a relational DB. Here is the code I was trying:
"roles": {
".read": "auth.uid != null",
"$rol_id": {
".write": "auth.uid != null",
".validate": "newData.hasChildren(['description', 'state'])",
"description": {
".validate": "newData.isString() &&
newData.val().matches(/[A-Za-z]$/i) &&
root.child('roles').child('$rol_id').child('description').val() !=
root.child('roles').child('$rol_id').child('description').exists()"
},
"state": {
".validate":"newData.isBoolean()"
}
}
},
The problem is that I can't enter in $rol_id unless i give it a constant value but i need it to evaluate in each object.
This is the structure from roles in firebase:
"roles" : {
"-KMohJaG6djjeBiq3oiV" : {
"creationDate" : 1468689365795,
"description" : "administrador",
"id" : "-KMohJaG6djjeBiq3oiV",
"permissions" : {
"inputs" : true,
"kardex" : true,
"outputs" : true,
"persons" : true,
"product" : false,
"rol" : true,
"sales" : true,
"supplier" : true,
"user" : true
},
"state" : true
},
}
Related
I want to check if there exists a user that have email = someemail#gmai.com in the Firebase database.
I use this function and is download 50MB of data in my PC after 10 minute I get a response that exists. There is any way that I can get that less than 5 second I don't want to wait 10 minute.
in PHP is like the
SELECT FROM ALL USERS WERE EMAIL = 'george#gmail.com'
This is the database:
"users" : {
user: {
"email" : "george#gmail.com",
"custom_id" : 534253,
"description" : "some small description"
},
1754: {
"email" : "natassa#gmail.com", <---- i want to find if this email from 5000 users exist in database and if exist i want to return true
"custom_id" : 110571,
"description" : "some small description"
},
1755: {
"email" : "george#gmail.com",
"custom_id" : dsgfsdfds,
"description" : "some small description"
},
}
This function give me response after 10 min:
check_if_email_exist(email: string) {
this.users = this.db.list('/user', { query: {
orderByChild: 'email',
equalTo: x,
limitToLast: 10,
}} ) as FirebaseListObservable<Product[]>;
console.log(this.users);
return this.users;
}
OMG I find the problem thanx to https://stackoverflow.com/users/209103/frank-van-puffelen is say something about index and when I look in my chrome console I find warning that says something about index and when I look in the database rules I understand what is missing
I add this inside database rules
{
"rules": {
".read": "auth != null",
".write": "auth != null",
"needs": {
".read": "true",
".write": "auth != null",
".indexOn": "name"
},
"brands": {
".read": "true",
".write": "auth != null",
".indexOn": "name"
},
"products": {
".read": "true",
".write": "auth != null",
".indexOn": "custom_id" <========== This line you want
}
}
}
I have wrote on below rules for Get the value form chats with key createdAt But i cant able to get the values from Firebase DB. Rules are Below
"chats": {
".read" : true,
".write" : "auth !== null",
"messages" : {
".indexOn": ["userName", "createdAt", "userId"]
}
},
chats/messages.json?orderBy="createdAt"&startAt=1485920224250&print=pretty
You're missing a level in your rules:
"chats": {
".read" : true,
".write" : "auth !== null",
"$chatId": {
"messages" : {
".indexOn": ["userName", "createdAt", "userId"]
}
}
},
I have the following data structure:
{"applicants":[
{
"-KNbKoNzPGsz2TAQp-j9" : {
"email" : "zahavi#post.tau.ac.il",
"id" : "056042344",
"name" : "Jacob",
"prefix" : "Prof.",
"surname" : "Zahavi"
},
"-KNbWPpsrFGJBDaWK2EN" : {
"email" : "chamud#gmail.com",
"id" : "314965211",
"name" : "Ilay",
"prefix" : "Mr.",
"surname" : "Shvo"
},
"-KNd8HvkzAYi0LtG9qNj" : {
"email" : "zahavi#zpost.tau.ac.il",
"id" : "056042344",
"name" : "Jacob",
"prefix" : "Prof.",
"surname" : "Zahavi"
}]
}
}
I would like to enforce uniqueness rule on the field id, so it will not be possible to create two entries in applicants collection that has the same id value.
currently my rules are:
{
"rules": {
".read": true,
".write": true,
"Tables":{"applicants":{"id":{".indexOn":".value"}}}
}
}
I explored two possible solutions that are:
1. transaction. unfortunately i did not find a way to run transaction from a query.
2. rules. but failed to find something suitable.
Edit (from comments):
I tried the following rules:
{
"rules": {
".read": true,
".write": true,
"Tables": {
"applicants": {
"$app": {
"id": {
".indexOn": ".value",
".validate": "!root.child('Tables').child('applicants').child(newData.child('id').val()).exists()"
},
}
}
}
}
}
and I always got creation failed permission denied even for values that were not exist
I am wondering if it's possible to do the firebase authentication on strings? I have seen it being done on keys like -XDhabsuduydvtest <- random test key.
Now i have this structure:
{
"conversations" : {
"person1" : {
"person2" : {
"0" : 0,
"last_read" : 1460377167535
}
},
"person2" : {
"person1" : {
"0" : 0,
"last_read" : 1460377125515
}
}
},
"messages" : {
"eb-uuid-729fc0ac-49b8-48fa-a2ff-f2ada67b9e4c-person1" : {
"body" : "Dit is een test vanuit iOS",
"date" : 1460383996536,
"sender" : "eb-uuid-729fc0ac-49b8-48fa-a2ff-f2ada67b9e4c"
},
"person1-person2" : {
"-KF49xHKqnDawywJ9H0b" : {
"body" : "test message",
"date" : 1460375639190,
"sender" : "person1"
},
"-KF4Fc1KHH31O4_l0QWh" : {
"body" : "new",
"date" : 1460377125013,
"sender" : "person2"
}
}
},
"users" : {
"eb-uuid-729fc0ac-49b8-48fa-a2ff-f2ada67b9e4c" : {
"chat_enabled" : true,
"email" : "test#gmail.com",
"first_name" : "John",
"last_name" : "Smith",
"provider" : "password",
"push_muted" : false,
"push_token" : "some-push-token",
"uid" : "729fc0ac-49b8-48fa-a2ff-f2ada67b9e4c",
"username" : "johnsmith"
},
"person1" : {
"first_name" : "person",
"last_name" : "one"
},
"person2" : {
"first_name" : "person",
"last_name" : "two"
}
}
}
plus some security rule i tried, obviously i'd like to check if the uuid's are the same, and not only if one exists
{
"rules": {
"messages": {
"$conv":{
//Person can only read a conversation he/she is participating in
".write": true,
".read": true,
".indexOn": ["date"]
}
},
"users":{
"$ebuuid":{
".write": "root.child('users').child($ebuuid).hasChild('uid')",
".read": "root.child('users').child($ebuuid).hasChild('uid')"
}
},
"conversations":{
".write": "data.child('uid').val() === auth.uid",
".read": true
}
}
}
(Replaced images with text)
I'm really not sure how to go from here now .. the user has some uid but i'm not sure how to check it with whether he or she can post messages etc ..
I'm trying to create a twitter clone to learn to use Firebase and I would love to get a suggestion about how to create the database structure. My biggest concern is related to followers and how to create a timeline when you are following for example 500 users. You would need to perform 500 queries and sort somehow for datetime.
{
"followers" : {
"cesar" : {
"followers" : {
"cesar2" : true
},
"following" : {
"cesar2" : true
}
},
"cesar2" : {
"followers" : {
"cesar" : true
},
"following" : {
"cesar" : true
}
}
},
"tweet" : {
"cesar" : [ null, {
"content" : "tweet 1"
} ]
},
"users" : {
"cesar" : {
"name" : "César",
"notifications" : true,
"username" : "cesar"
},
"cesar2" : {
"name" : "César2",
"notifications" : false,
"username" : "cesar2"
}
}
}
See Firefeed, Firebase's open-source Twitter clone. It includes a walkthrough of the data structure it uses, which boils down to using a fan-out approach when new messages are posted. Here's a copy of the rules used, which describes the underlying data structure:
{
"rules": {
// All data is readable by anyone.
".read": true,
"people": {
// A list of users with their names on the site.
"$userid": {
// Only the user can write their own entry into this list.
".write": "$userid ==auth.uid"
}
},
"users": {
"$userid": {
// The user is allowed to write everything in their bucket.
".write": "$userid ==auth.uid",
"following": {
// The following list should only contain actual ids from the "people" list.
"$followingid": {
".validate": "root.child('people').hasChild($followingid)"
}
},
"followers": {
// Anyone can add themself to to this user's followers list.
"$followerid": {
".write": "$followerid ==auth.uid"
}
},
"feed": {
"$sparkid": {
// User A can write in user B's feed, but only if A is following B, and only for sparks for which they are the author.
".write": "root.child('users/' + $userid + '/following').hasChild(auth.uid) && root.child('sparks/' + $sparkid + '/author').val() ==auth.uid"
}
}
}
},
"sparks": {
// A global list of sparks (the "firehose").
"$sparkid": {
// Modifying an existing spark is not allowed.
".write": "!data.exists()",
// Every spark should have an author and a body.
".validate": "newData.hasChildren(['author', 'content'])",
// A user can attribute a spark only to themselves.
"author": {
".validate": "newData.val() ==auth.uid"
},
"content": {
".validate": "newData.isString()"
}
}
},
"recent-users": {
// Users can add themselves to the list of users with recent activity.
"$userid": {
".write": "$userid ==auth.uid"
}
},
"recent-sparks": {
// Authors of sparks can add their sparks to this list.
"$sparkid": {
".write": "root.child('sparks/' + $sparkid + '/author').val() ==auth.uid"
}
},
"search": {
"firstName": {
"$searchKey": {
".write": "auth != null && (root.child('people/' +auth.uid + '/firstName').val() + '|' + root.child('people/' +auth.uid + '/lastName').val() + '|' +auth.uid) == $searchKey && newData.val() ==auth.uid"
}
},
"lastName": {
"$searchKey": {
".write": "auth != null && (root.child('people/' +auth.uid + '/lastName').val() + '|' + root.child('people/' +auth.uid + '/firstName').val() + '|' +auth.uid) == $searchKey && newData.val() ==auth.uid"
}
}
}
}
}