Quy tắc bảo mật Cloud Firestore cho phép bạn kiểm soát quyền truy cập vào tài liệu và bộ sưu tập trong cơ sở dữ liệu của mình. Cú pháp các quy tắc linh hoạt cho phép bạn tạo các quy tắc phù hợp với bất kỳ thứ gì, từ tất cả các lần ghi vào toàn bộ cơ sở dữ liệu đến các hoạt động trên một tài liệu cụ thể.
Hướng dẫn này mô tả cú pháp và cấu trúc cơ bản của các quy tắc bảo mật. Kết hợp cú pháp này với các điều kiện quy tắc bảo mật để tạo ra các bộ quy tắc hoàn chỉnh.
Khai báo dịch vụ và cơ sở dữ liệu
Quy tắc bảo mật Cloud Firestore luôn bắt đầu bằng khai báo sau:
service cloud.firestore {
match /databases/{database}/documents {
// ...
}
}
Khai báo service cloud.firestore
dụng các quy tắc cho Cloud Firestore, ngăn ngừa xung đột giữa các Quy tắc bảo mật của Cloud Firestore và các quy tắc cho các sản phẩm khác như Cloud Storage.
Khai báo match /databases/{database}/documents
chỉ định rằng các quy tắc phải khớp với bất kỳ cơ sở dữ liệu Cloud Firestore nào trong dự án. Hiện tại mỗi dự án chỉ có một cơ sở dữ liệu duy nhất có tên (default)
.
Các quy tắc đọc / ghi cơ bản
Các quy tắc cơ bản bao gồm một câu lệnh match
chỉ định một đường dẫn tài liệu và một biểu thức allow
nêu chi tiết khi nào được phép đọc dữ liệu được chỉ định:
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>;
}
}
}
Tất cả các câu lệnh khớp phải trỏ đến tài liệu, không phải bộ sưu tập. Câu lệnh đối sánh có thể trỏ đến một tài liệu cụ thể, như trong match /cities/SF
hoặc sử dụng ký tự đại diện để trỏ đến bất kỳ tài liệu nào trong đường dẫn được chỉ định, như trong match /cities/{city}
.
Trong ví dụ trên, câu lệnh so khớp sử dụng cú pháp ký tự đại diện {city}
. Điều này có nghĩa là quy tắc áp dụng cho bất kỳ tài liệu nào trong bộ sưu tập cities
, chẳng hạn như /cities/SF
hoặc /cities/NYC
. Khi các biểu thức allow
trong câu lệnh so khớp được đánh giá, biến city
sẽ chuyển thành tên tài liệu thành phố, chẳng hạn như SF
hoặc NYC
.
Hoạt động chi tiết
Trong một số tình huống, sẽ rất hữu ích khi chia nhỏ việc read
và write
thành các thao tác chi tiết hơn. Ví dụ: ứng dụng của bạn có thể muốn thực thi các điều kiện khác nhau về tạo tài liệu so với xóa tài liệu. Hoặc bạn có thể muốn cho phép đọc tài liệu đơn lẻ nhưng từ chối các truy vấn lớn.
Quy tắc read
có thể được chia thành get
và list
, trong khi quy tắc write
có thể được chia thành create
, update
và 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>;
}
}
}
Dữ liệu phân cấp
Dữ liệu trong Cloud Firestore được sắp xếp thành các bộ sưu tập tài liệu và mỗi tài liệu có thể mở rộng hệ thống phân cấp thông qua các bộ sưu tập con. Điều quan trọng là phải hiểu cách các quy tắc bảo mật tương tác với dữ liệu phân cấp.
Hãy xem xét tình huống mà mỗi tài liệu trong bộ sưu tập cities
có chứa một bộ sưu tập phụ các landmarks
. Các quy tắc bảo mật chỉ áp dụng tại con đường phù hợp, do đó, các kiểm soát truy cập được xác định trên bộ sưu tập cities
không áp dụng cho bộ sưu tập phụ của landmarks
. Thay vào đó, hãy viết các quy tắc rõ ràng để kiểm soát quyền truy cập vào các bộ sưu tập con:
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>;
}
}
}
}
Khi lồng các câu lệnh so match
, đường dẫn của câu lệnh so match
bên trong luôn liên quan đến đường dẫn của câu lệnh so match
bên ngoài. Do đó, các bộ quy tắc sau là tương đương:
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>;
}
}
}
Các ký tự đại diện đệ quy
Nếu bạn muốn các quy tắc áp dụng cho phân cấp sâu tùy ý, hãy sử dụng cú pháp ký tự đại diện đệ quy, {name=**}
. Ví dụ:
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>;
}
}
}
Khi sử dụng cú pháp ký tự đại diện đệ quy, biến ký tự đại diện sẽ chứa toàn bộ đoạn đường dẫn phù hợp, ngay cả khi tài liệu nằm trong một bộ sưu tập con lồng nhau sâu. Ví dụ: các quy tắc được liệt kê ở trên sẽ khớp với một tài liệu được đặt tại /cities/SF/landmarks/coit_tower
và giá trị của biến document
sẽ là SF/landmarks/coit_tower
.
Tuy nhiên, lưu ý rằng hoạt động của các ký tự đại diện đệ quy phụ thuộc vào phiên bản quy tắc.
Phiên bản 1
Các quy tắc bảo mật sử dụng phiên bản 1 theo mặc định. Trong phiên bản 1, các ký tự đại diện đệ quy khớp với một hoặc nhiều mục đường dẫn. Chúng không khớp với một đường dẫn trống, vì vậy match /cities/{city}/{document=**}
khớp với tài liệu trong bộ sưu tập con nhưng không khớp với bộ sưu tập cities
, trong khi match /cities/{document=**}
khớp với cả hai tài liệu trong bộ sưu tập cities
và bộ sưu tập phụ.
Các ký tự đại diện đệ quy phải ở cuối câu lệnh so khớp.
Phiên bản 2
Trong phiên bản 2 của quy tắc bảo mật, các ký tự đại diện đệ quy khớp với không hoặc nhiều mục đường dẫn. match/cities/{city}/{document=**}
khớp với tài liệu trong bất kỳ bộ sưu tập con nào cũng như tài liệu trong bộ sưu tập cities
.
Bạn phải chọn tham gia phiên bản 2 bằng cách thêm rules_version = '2';
ở đầu các quy tắc bảo mật của bạn:
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>;
}
}
}
Bạn có thể có nhiều nhất một ký tự đại diện đệ quy cho mỗi câu lệnh so khớp, nhưng trong phiên bản 2, bạn có thể đặt ký tự đại diện này ở bất kỳ đâu trong câu lệnh so khớp. Ví dụ:
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>;
}
}
}
Nếu bạn sử dụng truy vấn nhóm bộ sưu tập , bạn phải sử dụng phiên bản 2, xem bảo mật truy vấn nhóm bộ sưu tập .
Các câu lệnh trùng khớp
Có thể một tài liệu khớp với nhiều hơn một câu lệnh match
. Trong trường hợp nhiều biểu thức allow
khớp với một yêu cầu, quyền truy cập được cho phép nếu bất kỳ điều kiện nào là 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;
}
}
}
Trong ví dụ trên, tất cả các lần đọc và ghi vào bộ sưu tập cities
sẽ được phép vì quy tắc thứ hai luôn true
, mặc dù quy tắc đầu tiên luôn false
.
Giới hạn quy tắc bảo mật
Khi bạn làm việc với các quy tắc bảo mật, hãy lưu ý các giới hạn sau:
Giới hạn | Thông tin chi tiết |
---|---|
Số lượng lệnh gọi exists() , get() và getAfter() tối đa cho mỗi yêu cầu |
Vượt quá một trong hai giới hạn dẫn đến lỗi bị từ chối cấp quyền. Một số cuộc gọi truy cập tài liệu có thể được lưu trong bộ nhớ cache và các cuộc gọi được lưu trong bộ nhớ cache không được tính vào giới hạn. |
Độ sâu câu lệnh match lồng nhau tối đa | 10 |
Độ dài đường dẫn tối đa, trong các phân đoạn đường dẫn, được phép trong một tập hợp các câu lệnh so match lồng nhau | 100 |
Số lượng biến nắm bắt đường dẫn tối đa được phép trong một tập hợp các câu lệnh so match lồng nhau | 20 |
Độ sâu cuộc gọi chức năng tối đa | 20 |
Số lượng tối đa các đối số của hàm | 7 |
Số lượng tối đa các ràng buộc biến let mỗi hàm | 10 |
Số lượng lệnh gọi hàm đệ quy hoặc tuần hoàn tối đa | 0 (không được phép) |
Số lượng biểu thức tối đa được đánh giá cho mỗi yêu cầu | 1.000 |
Kích thước tối đa của một bộ quy tắc | Bộ quy tắc phải tuân theo hai giới hạn kích thước:
|