Panduan ini dibuat berdasarkan mempelajari sintaks inti dari panduan bahasa Aturan Keamanan Firebase untuk menunjukkan cara menambahkan ketentuan ke Aturan Keamanan Firebase untuk Cloud Storage.
Elemen penyusun utama Aturan Keamanan Cloud Storage adalah kondisi . Kondisi adalah ekspresi boolean yang menentukan apakah operasi tertentu harus diizinkan atau ditolak. Untuk aturan dasar, menggunakan literal true
dan false
sebagai kondisi berfungsi dengan baik. Namun Aturan Keamanan Firebase untuk bahasa Cloud Storage memberi Anda cara untuk menulis kondisi yang lebih kompleks yang dapat:
- Periksa autentikasi pengguna
- Validasi data yang masuk
Autentikasi
Aturan Keamanan Firebase untuk Cloud Storage terintegrasi dengan Firebase Authentication untuk memberikan autentikasi berbasis pengguna yang andal ke Cloud Storage. Ini memungkinkan kontrol akses granular berdasarkan klaim token Firebase Authentication.
Saat pengguna yang diautentikasi melakukan permintaan terhadap Cloud Storage, variabel request.auth
diisi dengan uid
pengguna ( request.auth.uid
) serta klaim Firebase Authentication JWT ( request.auth.token
).
Selain itu, saat menggunakan autentikasi khusus, klaim tambahan muncul di kolom request.auth.token
.
Saat pengguna yang tidak diautentikasi melakukan permintaan, variabel request.auth
adalah null
.
Menggunakan data ini, ada beberapa cara umum untuk menggunakan autentikasi untuk mengamankan file:
- Publik: abaikan
request.auth
- Diautentikasi pribadi: periksa apakah
request.auth
bukannull
- Pengguna pribadi: periksa apakah
request.auth.uid
sama dengan pathuid
- Grup pribadi: periksa klaim token khusus untuk mencocokkan klaim yang dipilih, atau baca metadata file untuk melihat apakah ada bidang metadata
Publik
Aturan apa pun yang tidak mempertimbangkan konteks request.auth
dapat dianggap sebagai aturan public
, karena tidak mempertimbangkan konteks autentikasi pengguna. Aturan ini berguna untuk menampilkan data publik seperti aset game, file suara, atau konten statis lainnya.
// Anyone to read a public image if the file is less than 100kB // Anyone can upload a public file ending in '.txt' match /public/{imageId} { allow read: if resource.size < 100 * 1024; allow write: if imageId.matches(".*\\.txt"); }
Diautentikasi pribadi
Dalam kasus tertentu, Anda mungkin ingin data dapat dilihat oleh semua pengguna aplikasi Anda yang diautentikasi, tetapi tidak oleh pengguna yang tidak diautentikasi. Karena variabel request.auth
adalah null
untuk semua pengguna yang tidak diautentikasi, yang harus Anda lakukan adalah memeriksa apakah variabel request.auth
ada untuk meminta autentikasi:
// Require authentication on all internal image reads match /internal/{imageId} { allow read: if request.auth != null; }
Pengguna pribadi
Sejauh ini, kasus penggunaan yang paling umum untuk request.auth
adalah untuk memberikan izin granular kepada pengguna individual pada file mereka: mulai dari mengunggah gambar profil hingga membaca dokumen pribadi.
Karena file di Cloud Storage memiliki "jalur" lengkap ke file, yang diperlukan untuk membuat file dikontrol oleh pengguna adalah bagian dari informasi identitas pengguna yang unik di awalan nama file (seperti uid
pengguna) yang dapat diperiksa ketika aturan dievaluasi:
// Only a user can upload their profile picture, but anyone can view it match /users/{userId}/profilePicture.png { allow read; allow write: if request.auth.uid == userId; }
Grup pribadi
Kasus penggunaan lain yang sama-sama umum adalah mengizinkan izin grup pada suatu objek, seperti mengizinkan beberapa anggota tim untuk berkolaborasi pada dokumen bersama. Ada beberapa pendekatan untuk melakukan ini:
- Buat token khusus Firebase Authentication yang berisi informasi tambahan tentang anggota grup (seperti ID grup)
- Sertakan informasi grup (seperti ID grup atau daftar
uid
resmi) di metadata file
Setelah data ini disimpan dalam token atau metadata file, data tersebut dapat direferensikan dari dalam aturan:
// Allow reads if the group ID in your token matches the file metadata's `owner` property // Allow writes if the group ID is in the user's custom token match /files/{groupId}/{fileName} { allow read: if resource.metadata.owner == request.auth.token.groupId; allow write: if request.auth.token.groupId == groupId; }
Minta Evaluasi
Upload, download, perubahan metadata, dan penghapusan dievaluasi menggunakan request
yang dikirim ke Cloud Storage. Selain ID unik pengguna dan payload Firebase Authentication di objek request.auth
seperti yang dijelaskan di atas, variabel request
berisi jalur file tempat permintaan dilakukan, waktu saat permintaan diterima, dan nilai resource
baru jika permintaan adalah menulis.
Objek request
juga berisi ID unik pengguna dan muatan Firebase Authentication di objek request.auth
, yang akan dijelaskan lebih lanjut di bagian Keamanan Berbasis Pengguna pada dokumen.
Daftar lengkap properti di objek request
tersedia di bawah ini:
Properti | Jenis | Keterangan |
---|---|---|
auth | peta<string, string> | Saat pengguna masuk, uid , ID unik pengguna, dan token , peta klaim Firebase Authentication JWT. Jika tidak, itu akan menjadi null . |
params | peta<string, string> | Peta yang berisi parameter kueri permintaan. |
path | jalur | path yang mewakili jalur permintaan sedang dilakukan. |
resource | peta<string, string> | Nilai sumber daya baru, hanya ada pada permintaan write . |
time | cap waktu | Stempel waktu yang mewakili waktu server saat permintaan dievaluasi. |
Evaluasi Sumber Daya
Saat mengevaluasi aturan, Anda mungkin juga ingin mengevaluasi metadata file yang sedang diunggah, diunduh, diubah, atau dihapus. Ini memungkinkan Anda untuk membuat aturan yang kompleks dan kuat yang melakukan hal-hal seperti hanya mengizinkan file dengan tipe konten tertentu untuk diunggah, atau hanya file yang berukuran lebih besar dari ukuran tertentu yang akan dihapus.
Aturan Keamanan Firebase untuk Cloud Storage menyediakan metadata file di objek resource
, yang berisi pasangan kunci/nilai dari metadata yang muncul di objek Cloud Storage. Properti ini dapat diperiksa pada permintaan read
atau write
untuk memastikan integritas data.
Pada permintaan write
(seperti unggahan, pembaruan metadata, dan penghapusan), selain objek resource
, yang berisi metadata file untuk file yang saat ini ada di jalur permintaan, Anda juga memiliki kemampuan untuk menggunakan objek request.resource
, yang berisi subset dari metadata file yang akan ditulis jika penulisan diizinkan. Anda dapat menggunakan kedua nilai ini untuk memastikan integritas data atau menerapkan batasan aplikasi seperti jenis atau ukuran file.
Daftar lengkap properti di objek resource
tersedia di bawah ini:
Properti | Jenis | Keterangan |
---|---|---|
name | rangkaian | Nama lengkap objek |
bucket | rangkaian | Nama bucket tempat objek ini berada. |
generation | int | Pembuatan objek Google Cloud Storage dari objek ini. |
metageneration | int | Metagenerasi objek Google Cloud Storage dari objek ini. |
size | int | Ukuran objek dalam byte. |
timeCreated | cap waktu | Stempel waktu yang menunjukkan waktu pembuatan objek. |
updated | cap waktu | Stempel waktu yang menunjukkan waktu objek terakhir diperbarui. |
md5Hash | rangkaian | Hash MD5 dari objek. |
crc32c | rangkaian | Hash crc32c dari objek. |
etag | rangkaian | Etag yang terkait dengan objek ini. |
contentDisposition | rangkaian | Disposisi konten yang terkait dengan objek ini. |
contentEncoding | rangkaian | Encoding konten yang terkait dengan objek ini. |
contentLanguage | rangkaian | Bahasa konten yang terkait dengan objek ini. |
contentType | rangkaian | Jenis konten yang terkait dengan objek ini. |
metadata | peta<string, string> | Pasangan kunci/nilai tambahan, metadata khusus yang ditentukan pengembang. |
request.resource
berisi semua ini kecuali generation
, metageneration
, etag
, timeCreated
, dan updated
.
Tingkatkan dengan Cloud Firestore
Anda dapat mengakses dokumen di Cloud Firestore untuk mengevaluasi kriteria otorisasi lainnya.
Dengan menggunakan fungsi firestore.get()
dan firestore.exists()
, aturan keamanan Anda dapat mengevaluasi permintaan masuk terhadap dokumen di Cloud Firestore. Fungsi firestore.get()
dan firestore.exists()
keduanya mengharapkan jalur dokumen yang ditentukan sepenuhnya. Saat menggunakan variabel untuk membangun jalur untuk firestore.get()
dan firestore.exists()
, Anda harus secara eksplisit meng-escape variabel menggunakan sintaks $(variable)
.
Pada contoh di bawah ini, kita melihat aturan yang membatasi akses baca ke file hanya untuk pengguna yang menjadi anggota klub tertentu.
service firebase.storage { match /b/{bucket}/o { match /users/{club}/files/{fileId} { allow read: if club in firestore.get(/databases/(default)/documents/users/$(request.auth.id)).memberships } } }Pada contoh berikutnya, hanya teman pengguna yang dapat melihat foto mereka.
service firebase.storage { match /b/{bucket}/o { match /users/{userId}/photos/{fileId} { allow read: if firestore.exists(/databases/(default)/documents/users/$(userId)/friends/$(request.auth.id)) } } }
Setelah Anda membuat dan menyimpan Aturan Keamanan Cloud Storage pertama yang menggunakan fungsi Cloud Firestore ini, Anda akan diminta di konsol Firebase atau Firebase CLI untuk mengaktifkan izin untuk menghubungkan kedua produk.
Anda dapat menonaktifkan fitur tersebut dengan menghapus peran IAM, seperti yang dijelaskan dalam Mengelola dan menerapkan Aturan Keamanan Firebase .
Validasi data
Aturan Keamanan Firebase untuk Cloud Storage juga dapat digunakan untuk validasi data, termasuk memvalidasi nama dan jalur file serta properti metadata file seperti contentType
dan size
.
service firebase.storage { match /b/{bucket}/o { match /images/{imageId} { // Only allow uploads of any image file that's less than 5MB allow write: if request.resource.size < 5 * 1024 * 1024 && request.resource.contentType.matches('image/.*'); } } }
Fungsi khusus
Saat Aturan Keamanan Firebase Anda menjadi lebih kompleks, Anda mungkin ingin menggabungkan kumpulan kondisi dalam fungsi yang dapat Anda gunakan kembali di seluruh kumpulan aturan Anda. Aturan keamanan mendukung fungsi kustom. Sintaks untuk fungsi khusus agak mirip dengan JavaScript, tetapi fungsi Aturan Keamanan Firebase ditulis dalam bahasa khusus domain yang memiliki beberapa batasan penting:
- Fungsi hanya dapat berisi satu pernyataan
return
. Mereka tidak dapat berisi logika tambahan apa pun. Misalnya, mereka tidak dapat menjalankan loop atau memanggil layanan eksternal. - Fungsi dapat secara otomatis mengakses fungsi dan variabel dari ruang lingkup di mana mereka didefinisikan. Misalnya, fungsi yang ditentukan dalam cakupan
service firebase.storage
memiliki akses ke variabelresource
, dan hanya untuk Cloud Firestore, fungsi bawaan sepertiget()
danexists()
. - Fungsi dapat memanggil fungsi lain tetapi mungkin tidak berulang. Total kedalaman tumpukan panggilan dibatasi hingga 10.
- Dalam version
rules2
, fungsi dapat mendefinisikan variabel menggunakan kata kuncilet
. Fungsi dapat memiliki sejumlah let binding, tetapi harus diakhiri dengan pernyataan pengembalian.
Suatu fungsi didefinisikan dengan kata kunci function
dan mengambil nol atau lebih argumen. Misalnya, Anda mungkin ingin menggabungkan dua jenis kondisi yang digunakan dalam contoh di atas menjadi satu fungsi:
service firebase.storage {
match /b/{bucket}/o {
// True if the user is signed in or the requested data is 'public'
function signedInOrPublic() {
return request.auth.uid != null || resource.data.visibility == 'public';
}
match /images/{imageId} {
allow read, write: if signedInOrPublic();
}
match /mp3s/{mp3Ids} {
allow read: if signedInOrPublic();
}
}
}
Menggunakan fungsi dalam Aturan Keamanan Firebase membuatnya lebih dapat dipertahankan seiring dengan meningkatnya kompleksitas aturan Anda.
Langkah selanjutnya
Setelah pembahasan ketentuan ini, Anda memiliki pemahaman Aturan yang lebih canggih dan siap untuk:
Pelajari cara menangani kasus penggunaan inti, dan pelajari alur kerja untuk mengembangkan, menguji, dan menerapkan Aturan:
- Tulis aturan yang membahas skenario umum .
- Kembangkan pengetahuan Anda dengan meninjau situasi di mana Anda harus melihat dan menghindari Aturan yang tidak aman .
- Uji aturan menggunakan emulator Cloud Storage dan pustaka uji Aturan Keamanan khusus .
- Tinjau metode yang tersedia untuk menerapkan Rules .