Membuat struktur aturan keamanan
Dengan Aturan Keamanan Firestore, Anda dapat mengontrol akses ke dokumen dan koleksi di database. Dengan sintaks aturan yang fleksibel, Anda dapat membuat aturan yang cocok dengan apa pun, dari penulisan ke seluruh database hingga operasi pada dokumen tertentu.
Panduan ini menjelaskan struktur dan sintaksis dasar aturan keamanan. Gabungkan sintaksis ini dengan kondisi aturan keamanan untuk membuat seperangkat aturan lengkap.
Deklarasi layanan dan database
Aturan Keamanan Firestore selalu dimulai dengan deklarasi berikut:
service cloud.firestore {
match /databases/{database}/documents {
// ...
}
}
Deklarasi service cloud.firestore
mencakup aturan untuk Firestore, sehingga mencegah konflik antara Aturan Keamanan Firestore dan aturan untuk produk lain seperti Cloud Storage.
Deklarasi match /databases/{database}/documents
menentukan bahwa aturan harus cocok dengan database Firestore mana pun dalam project. Saat ini setiap project hanya memiliki satu database bernama (default)
.
Aturan baca/tulis dasar
Aturan dasar terdiri atas pernyataan match
yang menentukan lokasi dokumen dan detail ekspresi allow
saat diizinkan membaca data yang ditentukan:
service cloud.firestore {
match /databases/{database}/documents {
// Match any document in the 'cities' collection
match /cities/{city} {
allow read: if <condition>;
allow write: if <condition>;
}
}
}
Semua pernyataan kecocokan harus mengarah ke dokumen, bukan koleksi. Pernyataan kecocokan dapat mengarah ke dokumen tertentu, seperti di match /cities/SF
atau menggunakan karakter pengganti untuk mengarah ke dokumen apa pun di jalur yang ditentukan, seperti di match /cities/{city}
.
Pada contoh di atas, pernyataan kecocokan menggunakan sintaksis karakter pengganti {city}
.
Artinya, aturan tersebut berlaku untuk setiap dokumen dalam koleksi cities
, seperti /cities/SF
atau /cities/NYC
. Saat ekspresi allow
dalam pernyataan kecocokan dievaluasi, variabel city
akan diselesaikan menjadi nama dokumen kota, seperti SF
atau NYC
.
Operasi terperinci
Dalam beberapa situasi, read
dan write
perlu dipecah menjadi operasi yang lebih terperinci agar memudahkan. Misalnya, aplikasi Anda mungkin ingin memberlakukan kondisi pada pembuatan dokumen yang berbeda dari kondisi pada penghapusan dokumen. Atau, Anda mungkin ingin mengizinkan pembacaan dokumen tunggal, tetapi menolak kueri yang besar.
Aturan read
dapat dibagi menjadi get
dan list
, sementara aturan write
dapat dibagi menjadi create
, update
, dan delete
:
service cloud.firestore {
match /databases/{database}/documents {
// A read rule can be divided into get and list rules
match /cities/{city} {
// Applies to single document read requests
allow get: if <condition>;
// Applies to queries and collection read requests
allow list: if <condition>;
}
// A write rule can be divided into create, update, and delete rules
match /cities/{city} {
// Applies to writes to nonexistent documents
allow create: if <condition>;
// Applies to writes to existing documents
allow update: if <condition>;
// Applies to delete operations
allow delete: if <condition>;
}
}
}
Data hierarkis
Data di Firestore disusun menjadi koleksi dokumen, dan setiap dokumen dapat memperluas hierarkinya berupa subkoleksi. Anda perlu memahami interaksi antara aturan keamanan dan data hierarkis.
Ambil contoh situasi ketika setiap dokumen dalam koleksi cities
berisi subkoleksi landmarks
. Aturan keamanan hanya berlaku di jalur yang cocok, sehingga kontrol akses yang ditetapkan pada koleksi cities
tidak berlaku untuk subkoleksi landmarks
. Sebagai gantinya, tulis aturan eksplisit untuk mengontrol akses ke subkoleksi:
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>;
}
}
}
}
Saat membuat pernyataan match
bertingkat, jalur pernyataan match
dalam selalu bersifat relatif terhadap jalur pernyataan match
luar. Oleh karena itu, kumpulan aturan berikut adalah setara:
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>;
}
}
}
Karakter pengganti rekursif
Jika Anda ingin aturan diterapkan ke sembarang hierarki bertingkat yang dalam, gunakan sintaksis karakter pengganti rekursif, {name=**}
. Contoh:
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>;
}
}
}
Jika menggunakan sintaksis karakter pengganti rekursif, variabel karakter pengganti akan memuat seluruh segmen lokasi yang cocok, meskipun jika dokumen tersebut berada di subkoleksi bertingkat yang dalam. Misalnya, aturan yang tercantum di atas akan cocok dengan dokumen yang terletak di /cities/SF/landmarks/coit_tower
, dan nilai variabel document
akan menjadi SF/landmarks/coit_tower
.
Namun, perlu diperhatikan bahwa perilaku karakter pengganti berulang bergantung pada versi aturan.
Versi 1
Aturan keamanan menggunakan versi 1 secara default. Dalam versi 1, karakter pengganti berulang cocok dengan satu atau beberapa item jalur. Karakter pengganti tersebut tidak cocok dengan jalur yang kosong, sehingga match /cities/{city}/{document=**}
cocok dengan dokumen di subkoleksi, bukan di koleksi cities
, sedangkan match /cities/{document=**}
cocok dengan dokumen dalam koleksi dan subkoleksi cities
.
Karakter pengganti berulang harus ada di akhir pernyataan yang cocok.
Versi 2
Pada aturan keamanan versi 2, karakter pengganti berulang cocok dengan nol atau beberapa item jalur. match/cities/{city}/{document=**}
mencocokkan dokumen di subkoleksi apa pun serta dokumen di koleksi cities
.
Anda harus memilih versi 2 dengan menambahkan rules_version = '2';
di bagian atas aturan keamanan Anda:
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>;
}
}
}
Anda dapat memiliki maksimal satu karakter pengganti berulang di setiap pernyataan kecocokan, tetapi dalam versi 2, Anda dapat menempatkan karakter pengganti ini di mana saja dalam pernyataan kecocokan. Contoh:
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>;
}
}
}
Jika menggunakan kueri grup koleksi, Anda harus menggunakan versi 2. Baca bagian mengamankan kueri grup koleksi.
Pernyataan kecocokan yang tumpang tindih
Ada kemungkinan dokumen cocok dengan beberapa pernyataan match
. Jika beberapa ekspresi allow
cocok dengan suatu permintaan, akses akan diizinkan jika salah satu kondisi tersebut adalah 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 or subcollections.
match /cities/{document=**} {
allow read, write: if true;
}
}
}
Pada contoh di atas, semua operasi baca dan tulis ke koleksi cities
akan diizinkan karena aturan kedua selalu true
, meskipun aturan pertama selalu false
.
Batas aturan keamanan
Perhatikan batas berikut saat menangani aturan keamanan:
Batas | Detail |
---|---|
Jumlah maksimum panggilan exists() , get() , dan getAfter() per permintaan |
Melebihi salah satu batas akan menyebabkan error izin ditolak. Beberapa panggilan akses dokumen dapat disimpan dalam cache, dan panggilan yang disimpan dalam cache tidak diperhitungkan dalam batas tersebut. |
Kedalaman maksimum pernyataan match bertingkat |
10 |
Panjang jalur maksimum, pada segmen jalur, yang diizinkan dalam sekumpulan pernyataan
match bertingkat |
100 |
Jumlah maksimum variabel tangkapan jalur yang diizinkan dalam sekumpulan pernyataan
match bertingkat |
20 |
Kedalaman maksimum panggilan fungsi | 20 |
Jumlah maksimum argumen fungsi | 7 |
Jumlah maksimum binding variabel let per fungsi |
10 |
Jumlah maksimum panggilan fungsi siklis atau berulang | 0 (tidak diizinkan) |
Jumlah maksimum ekspresi yang dievaluasi per permintaan | 1.000 |
Ukuran maksimum kumpulan aturan | Kumpulan aturan harus mematuhi dua batas ukuran:
|
Langkah berikutnya
- Tulis kondisi aturan keamanan kustom.
- Baca referensi aturan keamanan.