يمكن أن يكون الأمان أحد أكثر أجزاء عملية تطوير التطبيقات تعقيدًا. في معظم التطبيقات، على المطوّرين إنشاء خادم وتشغيله يتولّى عملية المصادقة (تحديد هوية المستخدم) والتفويض (تحديد الإجراءات التي يمكن للمستخدم تنفيذها).
Firebase Security Rules إزالة الطبقة الوسطى (الخادم) والسماح لك بتحديد أذونات مستندة إلى المسار للعملاء الذين يتصلون ببياناتك مباشرةً استخدِم هذا الدليل للاطّلاع على مزيد من المعلومات حول كيفية تطبيق القواعد على الطلبات الواردة.
اختَر منتجًا لمعرفة المزيد من المعلومات عن قواعده.
Cloud Firestore
البنية الأساسية
Firebase Security Rules في Cloud Firestore وCloud Storage، استخدِم البنية والصيغة التاليتَين:
service <<name>> {
// Match the resource path.
match <<path>> {
// Allow the request if the following conditions are true.
allow <<methods>> : if <<condition>>
}
}
في ما يلي المفاهيم الأساسية المهمة التي يجب فهمها أثناء إنشاء القواعد:
- الطلب: الطريقة أو الطرق التي تم استدعاؤها في عبارة
allow
هذه هي الطرق التي تسمح بتنفيذها. الطرق العادية هي:get
وlist
وcreate
وupdate
وdelete
. تتيح طريقتَاread
وwrite
المريحتان إمكانية الوصول إلى قاعدة البيانات أو مسار التخزين المحدّدَين للقراءة والكتابة على نطاق واسع. - المسار: قاعدة البيانات أو موقع التخزين، ويتم تمثيلهما كمسار URI.
- القاعدة: عبارة
allow
، التي تتضمّن شرطًا يسمح بتقديم طلب إذا تم تقييمه على أنّه صحيح.
الإصدار 2 من قواعد الأمان
اعتبارًا من أيار (مايو) 2019، أصبح الإصدار 2 من Firebase لقواعد الأمان متاحًا. تغيّر النسخة 2 من القواعد سلوك أحرف البدل
التكرارية {name=**}
. يجب استخدام الإصدار 2 إذا كنت تخطّط لاستخدام طلبات مجموعة البيانات. يجب الموافقة على استخدام الإصدار 2 من خلال وضع rules_version = '2';
في السطر الأول من قواعد الأمان:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
المسارات المطابقة
يجب أن تشير جميع عبارات المطابقة إلى مستندات وليس إلى مجموعات. يمكن أن يشير بيان المطابقة إلى مستند معيّن، كما في match /cities/SF
، أو استخدام أحرف بدل للإشارة إلى أي مستند في المسار المحدّد، كما في match /cities/{city}
.
في المثال، تستخدم عبارة المطابقة بنية حرف البدل {city}
.
وهذا يعني أنّ القاعدة تنطبق على أي مستند في المجموعة cities
، مثل /cities/SF
أو /cities/NYC
. عند تقييم تعبيرات allow
في عبارة المطابقة، سيتم تحويل المتغيّر city
إلى اسم مستند المدينة، مثل SF
أو NYC
.
المجموعات الفرعية المطابقة
يتم تنظيم البيانات في Cloud Firestore في مجموعات من المستندات، ويمكن لكل مستند توسيع التسلسل الهرمي من خلال مجموعات فرعية. من المهم فهم كيفية تفاعل قواعد الأمان مع البيانات الهرمية.
لنفترض أنّ كل مستند في المجموعة cities
يحتوي على مجموعة فرعية landmarks
. لا تنطبق قواعد الأمان إلا على المسار المطابِق، لذا لا تنطبق عناصر التحكّم في الوصول المحدّدة في المجموعة cities
على المجموعة الفرعية landmarks
. بدلاً من ذلك، اكتب قواعد صريحة للتحكّم في الوصول إلى المجموعات الفرعية:
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city} {
allow read, write: if <condition>;
// Explicitly define rules for the 'landmarks' subcollection
match /landmarks/{landmark} {
allow read, write: if <condition>;
}
}
}
}
عند تضمين عبارات match
، يكون مسار عبارة match
الداخلية دائمًا نسبيًا إلى مسار عبارة match
الخارجية. وبالتالي، فإنّ مجموعات القواعد التالية متكافئة:
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city} {
match /landmarks/{landmark} {
allow read, write: if <condition>;
}
}
}
}
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city}/landmarks/{landmark} {
allow read, write: if <condition>;
}
}
}
عبارات المطابقة المتداخلة
من المحتمل أن يتطابق المستند مع أكثر من بيان match
واحد. في حال تطابق تعبيرات allow
متعددة مع أحد الطلبات، سيتم السماح بالوصول إذا كان أي من الشروط true
:
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the 'cities' collection.
match /cities/{city} {
allow read, write: if false;
}
// Matches any document in the 'cities' collection.
match /cities/{document} {
allow read, write: if true;
}
}
}
في المثال، سيتم السماح بجميع عمليات القراءة والكتابة في المجموعة cities
لأنّ القاعدة الثانية هي دائمًا true
، حتى لو كانت القاعدة الأولى هي دائمًا false
.
أحرف البدل التكرارية
إذا كنت تريد تطبيق القواعد على تسلسل هرمي عميق بشكل عشوائي، استخدِم بنية أحرف البدل المتكررة، {name=**}
:
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the cities collection as well as any document
// in a subcollection.
match /cities/{document=**} {
allow read, write: if <condition>;
}
}
}
عند استخدام بنية حرف البدل المتكرّر، سيحتوي متغيّر حرف البدل على جزء المسار المطابق بالكامل، حتى إذا كان المستند يقع في مجموعة فرعية متداخلة بشكل كبير. على سبيل المثال، ستتطابق القواعد المدرَجة مع مستند يقع في /cities/SF/landmarks/coit_tower
، وستكون قيمة المتغيّر document
هي SF/landmarks/coit_tower
.
يُرجى العِلم أنّ سلوك أحرف البدل المتكرّرة يعتمد على إصدار القواعد.
الإصدار 1
تستخدم قواعد الأمان الإصدار 1 تلقائيًا. في الإصدار 1، تتطابق أحرف البدل المتكررة مع عنصر واحد أو أكثر من عناصر المسار. ولا تتطابق مع مسار فارغ، لذا فإنّ
match /cities/{city}/{document=**}
تتطابق مع المستندات في المجموعات الفرعية ولكن ليس في المجموعة cities
، بينما تتطابق match /cities/{document=**}
مع المستندات في المجموعة cities
والمجموعات الفرعية.
يجب أن تأتي أحرف البدل المتكررة في نهاية عبارة مطابقة.
الإصدار 2
في الإصدار 2 من قواعد الأمان، تتطابق أحرف البدل المتكررة مع صفر أو أكثر من عناصر المسار. تطابق match/cities/{city}/{document=**}
المستندات في أي مجموعات فرعية بالإضافة إلى المستندات في المجموعة cities
.
يجب الموافقة على استخدام الإصدار 2 من خلال إضافة rules_version = '2';
في أعلى قواعد الأمان:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the cities collection as well as any document
// in a subcollection.
match /cities/{city}/{document=**} {
allow read, write: if <condition>;
}
}
}
يمكنك استخدام حرف بدل متكرّر واحد على الأكثر لكل عبارة مطابقة، ولكن في الإصدار 2، يمكنك وضع حرف البدل هذا في أي مكان في عبارة المطابقة. على سبيل المثال:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the songs collection group
match /{path=**}/songs/{song} {
allow read, write: if <condition>;
}
}
}
في حال استخدام طلبات البحث في مجموعة المستندات، يجب استخدام الإصدار 2، راجِع تأمين طلبات البحث في مجموعة المستندات.
حدود قواعد الأمان
أثناء العمل باستخدام قواعد الأمان، يُرجى مراعاة الحدود التالية:
الحدّ | التفاصيل |
---|---|
الحد الأقصى لعدد طلبات exists() وget() وgetAfter() في كل طلب |
وسيؤدي تجاوز أي من الحدّين إلى ظهور خطأ متعلق برفض الإذن. قد يتم تخزين بعض طلبات الوصول إلى المستندات مؤقتًا، ولا يتم احتساب الطلبات المخزّنة مؤقتًا ضمن الحدود. |
الحد الأقصى لعمق عبارة match المتداخلة |
10 |
الحد الأقصى لطول المسار، بوحدات المسار، المسموح به ضمن مجموعة من عبارات match المتداخلة |
100 |
الحد الأقصى لعدد متغيرات التقاط المسار المسموح بها ضمن مجموعة من عبارات match المتداخلة |
20 |
الحد الأقصى لمستوى استدعاء الدالة | 20 |
الحدّ الأقصى لعدد وسيطات الدالة | 7 |
الحدّ الأقصى لعدد عمليات ربط المتغيّرات let لكل دالة |
10 |
الحدّ الأقصى لعدد استدعاءات الدوال المتكرّرة أو الدورية | 0 (غير مسموح به) |
الحد الأقصى لعدد التعبيرات التي يتم تقييمها لكل طلب | 1,000 |
الحدّ الأقصى لحجم مجموعة القواعد | يجب أن تلتزم مجموعات القواعد بحدّين للحجم:
|
Cloud Storage
البنية الأساسية
Firebase Security Rules في Cloud Firestore وCloud Storage، استخدِم البنية والصيغة التاليتَين:
service <<name>> {
// Match the resource path.
match <<path>> {
// Allow the request if the following conditions are true.
allow <<methods>> : if <<condition>>
}
}
في ما يلي المفاهيم الأساسية المهمة التي يجب فهمها أثناء إنشاء القواعد:
- الطلب: الطريقة أو الطرق التي تم استدعاؤها في عبارة
allow
هذه هي الطرق التي تسمح بتنفيذها. الطرق العادية هي:get
وlist
وcreate
وupdate
وdelete
. تتيح طريقتَاread
وwrite
المريحتان إمكانية الوصول إلى قاعدة البيانات أو مسار التخزين المحدّدَين للقراءة والكتابة على نطاق واسع. - المسار: قاعدة البيانات أو موقع التخزين، ويتم تمثيلهما كمسار URI.
- القاعدة: عبارة
allow
، التي تتضمّن شرطًا يسمح بتقديم طلب إذا تم تقييمه على أنّه صحيح.
المسارات المطابقة
Cloud Storage Security Rules match
مسارات الملفات المستخدَمة للوصول إلى الملفات في Cloud Storage يمكن أن تتضمّن القواعد match
مسارات دقيقة أو مسارات أحرف بدل، ويمكن أيضًا أن تكون القواعد متداخلة. إذا لم تسمح أي قاعدة مطابقة بطريقة طلب، أو إذا تم تقييم الشرط على أنّه false
، سيتم رفض الطلب.
المطابقات التامة
// Exact match for "images/profilePhoto.png" match /images/profilePhoto.png { allow write: if <condition>; } // Exact match for "images/croppedProfilePhoto.png" match /images/croppedProfilePhoto.png { allow write: if <other_condition>; }
المطابقات المتداخلة
// Partial match for files that start with "images" match /images { // Exact match for "images/profilePhoto.png" match /profilePhoto.png { allow write: if <condition>; } // Exact match for "images/croppedProfilePhoto.png" match /croppedProfilePhoto.png { allow write: if <other_condition>; } }
المطابقات التي تتضمّن أحرف بدل
يمكن أيضًا استخدام القواعد match
نمطًا باستخدام أحرف البدل. حرف البدل هو متغيّر مسمّى يمثّل إما سلسلة واحدة مثل profilePhoto.png
أو عدة أجزاء من المسار، مثل images/profilePhoto.png
.
يتم إنشاء حرف بدل من خلال إضافة أقواس معقوفة حول اسم حرف البدل، مثل {string}
. يمكن تحديد حرف بدل لعدة أجزاء من خلال إضافة =**
إلى اسم حرف البدل، مثل {path=**}
:
// Partial match for files that start with "images" match /images { // Exact match for "images/*" // e.g. images/profilePhoto.png is matched match /{imageId} { // This rule only matches a single path segment (*) // imageId is a string that contains the specific segment matched allow read: if <condition>; } // Exact match for "images/**" // e.g. images/users/user:12345/profilePhoto.png is matched // images/profilePhoto.png is also matched! match /{allImages=**} { // This rule matches one or more path segments (**) // allImages is a path that contains all segments matched allow read: if <other_condition>; } }
إذا تطابقت عدة قواعد مع ملف، تكون النتيجة هي OR
لنتيجة تقييم جميع القواعد. أي أنّه إذا كان أي قاعدة يتطابق معها الملف يتم تقييمها على أنّها true
، تكون النتيجة true
.
في القواعد، يمكن قراءة الملف "images/profilePhoto.png" إذا كانت قيمة condition
أو other_condition
صحيحة، بينما يخضع الملف "images/users/user:12345/profilePhoto.png" لنتيجة other_condition
فقط.
يمكن الإشارة إلى متغيّر حرف البدل من داخل match
provide filename
أو ترخيص المسار:
// Another way to restrict the name of a file match /images/{imageId} { allow read: if imageId == "profilePhoto.png"; }
Cloud Storage Security Rules لا تتتالى، ولا يتم تقييم القواعد إلا عندما يتطابق مسار الطلب مع مسار يتضمّن قواعد محددة.
طلب التقييم
يتم تقييم عمليات التحميل والتنزيل وتغييرات البيانات الوصفية وعمليات الحذف باستخدام
request
المُرسَلة إلى Cloud Storage. يحتوي المتغيّر request
على المسار الذي يتم فيه تنفيذ الطلب، والوقت الذي تم فيه تلقّي الطلب، وقيمة resource
الجديدة إذا كان الطلب عبارة عن عملية كتابة. يتم أيضًا تضمين عناوين HTTP وحالة المصادقة.
يحتوي العنصر request
أيضًا على المعرّف الفريد للمستخدم والحمولة Firebase Authentication في العنصر request.auth
، وسيتم توضيح ذلك بالتفصيل في قسم المصادقة من المستندات.
في ما يلي قائمة كاملة بالسمات في العنصر request
:
الموقع | النوع | الوصف |
---|---|---|
auth |
map<string, string> | عندما يسجّل المستخدم الدخول، يتم تقديم uid ، وهو المعرّف الفريد للمستخدم، وtoken ، وهي خريطة لطلبات Firebase Authentication JWT. بخلاف ذلك، ستكون القيمة
null . |
params |
map<string, string> | خريطة تحتوي على مَعلمات طلب البحث. |
path |
المسار | تمثّل path المسار الذي يتم تنفيذ الطلب فيه. |
resource |
map<string, string> | قيمة المورد الجديدة، وهي متوفّرة فقط في طلبات write .
|
time |
الطابع الزمني | طابع زمني يمثّل وقت الخادم الذي يتم فيه تقييم الطلب. |
تقييم الموارد
عند تقييم القواعد، قد تحتاج أيضًا إلى تقييم البيانات الوصفية للملف الذي يتم تحميله أو تنزيله أو تعديله أو حذفه. يتيح لك ذلك إنشاء قواعد معقّدة وفعّالة تنفّذ إجراءات مثل السماح فقط بتحميل الملفات التي تتضمّن أنواع محتوى معيّنة، أو حذف الملفات التي يزيد حجمها عن حجم معيّن فقط.
يوفر Firebase Security Rules الخاص بـ Cloud Storage البيانات الوصفية للملف في كائن resource
،
الذي يحتوي على أزواج مفتاح/قيمة للبيانات الوصفية المعروضة في كائن Cloud Storage. يمكن فحص هذه السمات في طلبات read
أو write
لضمان سلامة البيانات.
في طلبات write
(مثل عمليات التحميل وتعديل البيانات الوصفية والحذف)، بالإضافة إلى عنصر resource
الذي يحتوي على البيانات الوصفية للملف الموجود في مسار الطلب، يمكنك أيضًا استخدام عنصر request.resource
الذي يحتوي على مجموعة فرعية من البيانات الوصفية للملف المطلوب كتابتها إذا كان مسموحًا بالكتابة. يمكنك استخدام هاتين القيمتين لضمان سلامة البيانات أو فرض قيود على التطبيق، مثل نوع الملف أو حجمه.
تتوفّر قائمة كاملة بالخصائص في العنصر resource
:
الموقع | النوع | الوصف |
---|---|---|
name |
سلسلة | الاسم الكامل للعنصر |
bucket |
سلسلة | اسم الحزمة التي يقيم فيها هذا العنصر. |
generation |
int | تمثّل هذه السمة Google Cloud Storage الجيل الذي تم فيه إنشاء العنصر. |
metageneration |
int | تمثّل هذه السمة Google Cloud Storage الجيل الوصفي للعنصر. |
size |
int | حجم الكائن بالبايت |
timeCreated |
الطابع الزمني | طابع زمني يمثّل وقت إنشاء عنصر. |
updated |
الطابع الزمني | طابع زمني يمثّل وقت آخر تعديل تم إجراؤه على أحد العناصر |
md5Hash |
سلسلة | تجزئة MD5 للعنصر |
crc32c |
سلسلة | تتضمّن هذه السمة قيمة التجزئة crc32c الخاصة بالكائن. |
etag |
سلسلة | تمثّل هذه السمة علامة etag المرتبطة بهذا العنصر. |
contentDisposition |
سلسلة | تمثّل هذه السمة طريقة عرض المحتوى المرتبطة بهذا العنصر. |
contentEncoding |
سلسلة | تمثّل هذه السمة ترميز المحتوى المرتبط بهذا العنصر. |
contentLanguage |
سلسلة | تمثّل هذه السمة لغة المحتوى المرتبطة بهذا العنصر. |
contentType |
سلسلة | تمثّل هذه السمة نوع المحتوى المرتبط بهذا العنصر. |
metadata |
map<string, string> | أزواج المفاتيح والقيم للبيانات الوصفية المخصّصة الإضافية التي يحدّدها المطوّر |
يحتوي request.resource
على كل هذه القيم باستثناء generation
وmetageneration
وetag
وtimeCreated
وupdated
.
حدود قواعد الأمان
أثناء العمل باستخدام قواعد الأمان، يُرجى مراعاة الحدود التالية:
الحدّ | التفاصيل |
---|---|
الحد الأقصى لعدد طلبات firestore.exists() وfirestore.get() لكل طلب |
2 لطلبات المستندات الفردية وطلبات البحث ويؤدي تجاوز هذا الحد إلى ظهور خطأ "تم رفض الإذن". قد يتم تخزين عمليات الوصول إلى المستندات نفسها مؤقتًا، ولا يتم احتساب عمليات الوصول المخزَّنة مؤقتًا ضمن الحدود. |
مثال كامل
بوضع كل ذلك معًا، يمكنك إنشاء مثال كامل على قواعد لحل تخزين الصور:
service firebase.storage { match /b/{bucket}/o { match /images { // Allow write files to the path "images/*", subject to the constraints: // 1) File is less than 5MB // 2) Content type is an image // 3) Uploaded content type matches existing content type // 4) Filename (stored in imageId wildcard variable) is less than 32 characters match /{imageId} { allow read; allow write: if request.resource.size < 5 * 1024 * 1024 && request.resource.contentType.matches('image/.*') && request.resource.contentType == resource.contentType && imageId.size() < 32 } } } }
Realtime Database
البنية الأساسية
في Realtime Database، يتألف Firebase Security Rules من عبارات شبيهة بـ JavaScript مضمّنة في مستند JSON.
يستخدمون بنية الجملة التالية:
{
"rules": {
"<<path>>": {
// Allow the request if the condition for each method is true.
".read": <<condition>>,
".write": <<condition>>,
".validate": <<condition>>
}
}
}
تتضمّن القاعدة ثلاثة عناصر أساسية:
- المسار: موقع قاعدة البيانات وهي تتطابق مع بنية JSON لقاعدة البيانات.
- الطلب: هذه هي الطرق التي تستخدمها القاعدة لمنح الإذن بالوصول. تمنح قواعد
read
وwrite
إذن وصول واسع النطاق للقراءة والكتابة، بينما تعمل قواعدvalidate
كعملية تحقق ثانوية لمنح إذن الوصول استنادًا إلى البيانات الواردة أو الحالية. - الشرط: الشرط الذي يسمح بتنفيذ الطلب إذا تم تقييمه على أنّه صحيح.
كيفية تطبيق القواعد على المسارات
في Realtime Database، يتم تطبيق Rules بشكل ذري، ما يعني أنّ القواعد في عُقد الأب ذات المستوى الأعلى تلغي القواعد في عُقد الأبناء الأكثر دقة، ولا يمكن للقواعد في العقدة الأعمق منح إذن الوصول إلى مسار الأب. لا يمكنك تحسين أو إبطال إذن الوصول إلى مسار أعمق في بنية قاعدة البيانات إذا سبق لك منح الإذن لأحد المسارات الرئيسية.
يجب مراعاة القواعد التالية:
{ "rules": { "foo": { // allows read to /foo/* ".read": "data.child('baz').val() === true", "bar": { // ignored, since read was allowed already ".read": false } } } }
تسمح بنية الأمان هذه بقراءة /bar/
من أي مكان يحتوي فيه /foo/
على عنصر فرعي baz
بالقيمة true
.
لا يكون لقاعدة ".read": false
ضمن /foo/bar/
أي تأثير هنا، لأنّه لا يمكن إلغاء الإذن بالوصول باستخدام مسار فرعي.
على الرغم من أنّها قد لا تبدو بديهية على الفور، إلا أنّها جزء فعّال من لغة القواعد وتسمح بتنفيذ امتيازات وصول معقّدة للغاية بأقل جهد ممكن. ويفيد ذلك بشكل خاص في الأمان المستند إلى المستخدم.
ومع ذلك، لا تتتالى قواعد .validate
. يجب استيفاء جميع قواعد التحقّق من الصحة على جميع مستويات التسلسل الهرمي للسماح بالكتابة.
بالإضافة إلى ذلك، بما أنّ القواعد لا تنطبق على المسار الرئيسي، ستفشل عملية القراءة أو الكتابة إذا لم تكن هناك قاعدة في الموقع المطلوب أو في موقع رئيسي يمنح إذن الوصول. حتى إذا كان يمكن الوصول إلى كل مسار فرعي متأثر، سيتعذّر تمامًا القراءة في الموقع الرئيسي. إليك البنية التالية:
{ "rules": { "records": { "rec1": { ".read": true }, "rec2": { ".read": false } } } }
بدون فهم أنّ القواعد يتم تقييمها بشكل ذري، قد يبدو أنّ جلب المسار /records/
سيعرض rec1
ولكن ليس rec2
. ومع ذلك، فإنّ النتيجة الفعلية هي خطأ:
JavaScript
var db = firebase.database(); db.ref("records").once("value", function(snap) { // success method is not called }, function(err) { // error callback triggered with PERMISSION_DENIED });
Objective-C
FIRDatabaseReference *ref = [[FIRDatabase database] reference]; [[_ref child:@"records"] observeSingleEventOfType:FIRDataEventTypeValue withBlock:^(FIRDataSnapshot *snapshot) { // success block is not called } withCancelBlock:^(NSError * _Nonnull error) { // cancel block triggered with PERMISSION_DENIED }];
Swift
var ref = FIRDatabase.database().reference() ref.child("records").observeSingleEventOfType(.Value, withBlock: { snapshot in // success block is not called }, withCancelBlock: { error in // cancel block triggered with PERMISSION_DENIED })
Java
FirebaseDatabase database = FirebaseDatabase.getInstance(); DatabaseReference ref = database.getReference("records"); ref.addListenerForSingleValueEvent(new ValueEventListener() { @Override public void onDataChange(DataSnapshot snapshot) { // success method is not called } @Override public void onCancelled(FirebaseError firebaseError) { // error callback triggered with PERMISSION_DENIED }); });
REST
curl https://docs-examples.firebaseio.com/rest/records/ # response returns a PERMISSION_DENIED error
بما أنّ عملية القراءة في /records/
ذرية، ولا توجد قاعدة قراءة تمنح إذن الوصول إلى جميع البيانات ضِمن /records/
، سيؤدي ذلك إلى ظهور الخطأ PERMISSION_DENIED
. إذا قيّمنا هذه القاعدة في محاكي الأمان في وحدة تحكّم Firebase، يمكننا أن نرى أنّه تم رفض عملية القراءة:
Attempt to read /records with auth=Success(null) / /records No .read rule allowed the operation. Read was denied.
تم رفض العملية لأنّه لم تسمح أي قاعدة قراءة بالوصول إلى المسار /records/
، ولكن تجدر الإشارة إلى أنّه لم يتم تقييم القاعدة الخاصة بـ rec1
لأنّها لم تكن في المسار الذي طلبناه. لاسترداد rec1
، يجب الوصول إليه مباشرةً:
JavaScript
var db = firebase.database(); db.ref("records/rec1").once("value", function(snap) { // SUCCESS! }, function(err) { // error callback is not called });
Objective-C
FIRDatabaseReference *ref = [[FIRDatabase database] reference]; [[ref child:@"records/rec1"] observeSingleEventOfType:FEventTypeValue withBlock:^(FIRDataSnapshot *snapshot) { // SUCCESS! }];
Swift
var ref = FIRDatabase.database().reference() ref.child("records/rec1").observeSingleEventOfType(.Value, withBlock: { snapshot in // SUCCESS! })
Java
FirebaseDatabase database = FirebaseDatabase.getInstance(); DatabaseReference ref = database.getReference("records/rec1"); ref.addListenerForSingleValueEvent(new ValueEventListener() { @Override public void onDataChange(DataSnapshot snapshot) { // SUCCESS! } @Override public void onCancelled(FirebaseError firebaseError) { // error callback is not called } });
REST
curl https://docs-examples.firebaseio.com/rest/records/rec1 # SUCCESS!
متغيّر الموقع الجغرافي
تتيح Realtime Database وRules استخدام $location
متغيّر لمطابقة أجزاء المسار. استخدِم البادئة $
قبل جزء المسار لمطابقة القاعدة مع أي عقد فرعية على طول المسار.
{
"rules": {
"rooms": {
// This rule applies to any child of /rooms/, the key for each room id
// is stored inside $room_id variable for reference
"$room_id": {
"topic": {
// The room's topic can be changed if the room id has "public" in it
".write": "$room_id.contains('public')"
}
}
}
}
}
يمكنك أيضًا استخدام $variable
بالتوازي مع أسماء المسارات الثابتة.
{
"rules": {
"widget": {
// a widget can have a title or color attribute
"title": { ".validate": true },
"color": { ".validate": true },
// but no other child paths are allowed
// in this case, $other means any key excluding "title" and "color"
"$other": { ".validate": false }
}
}
}