กฎความปลอดภัยของ Cloud Firestore ช่วยให้คุณควบคุมการเข้าถึงเอกสารและคอลเลกชันในฐานข้อมูลของคุณ ไวยากรณ์กฎที่ยืดหยุ่นช่วยให้คุณสร้างกฎที่ตรงกับอะไรก็ได้ ตั้งแต่การเขียนทั้งหมดไปจนถึงฐานข้อมูลทั้งหมดไปจนถึงการดำเนินการในเอกสารเฉพาะ
คู่มือนี้จะอธิบายไวยากรณ์พื้นฐานและโครงสร้างของกฎความปลอดภัย รวมไวยากรณ์นี้เข้ากับ เงื่อนไขกฎความปลอดภัย เพื่อสร้างชุดกฎที่สมบูรณ์
การประกาศบริการและฐานข้อมูล
กฎความปลอดภัยของ Cloud Firestore จะเริ่มต้นด้วยการประกาศต่อไปนี้เสมอ:
service cloud.firestore {
match /databases/{database}/documents {
// ...
}
}
การประกาศ service cloud.firestore
จะกำหนดขอบเขตกฎไปยัง Cloud Firestore เพื่อป้องกันความขัดแย้งระหว่างกฎความปลอดภัยของ Cloud Firestore และกฎสำหรับผลิตภัณฑ์อื่นๆ เช่น Cloud Storage
การประกาศการจับ match /databases/{database}/documents
ระบุว่ากฎควรตรงกับฐานข้อมูล Cloud Firestore ในโปรเจ็กต์ ปัจจุบันแต่ละโครงการมีเพียงฐานข้อมูลเดียวที่ชื่อ (default)
กฎพื้นฐานการอ่าน/เขียน
กฎพื้นฐานประกอบด้วยคำสั่งการจับ match
ที่ระบุเส้นทางเอกสารและนิพจน์ allow
ที่ให้รายละเอียดเมื่ออ่านข้อมูลที่ระบุ:
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>;
}
}
}
ข้อความที่ตรงกันทั้งหมดควรชี้ไปที่เอกสาร ไม่ใช่คอลเลกชัน คำสั่งการจับคู่สามารถชี้ไปที่เอกสารเฉพาะ เช่น ใน match /cities/SF
หรือใช้ไวด์การ์ดเพื่อชี้ไปยังเอกสารใดๆ ในเส้นทางที่ระบุ เช่นใน match /cities/{city}
ในตัวอย่างข้างต้น คำสั่งการจับคู่ใช้ไวยากรณ์ไวด์การ์ด {city}
ซึ่งหมายความว่ากฎนี้ใช้กับเอกสารใดๆ ในคอลเลกชัน cities
เช่น /cities/SF
หรือ /cities/NYC
เมื่อมีการประเมินนิพจน์ allow
ในคำสั่งการจับคู่ ตัวแปร city
จะแปลงเป็นชื่อเอกสารเมือง เช่น SF
หรือ NYC
การดำเนินงานแบบละเอียด
ในบางสถานการณ์ การแยกย่อย read
และ write
ออกเป็นการดำเนินการที่ละเอียดยิ่งขึ้นจะมีประโยชน์ ตัวอย่างเช่น แอปของคุณอาจต้องการบังคับใช้เงื่อนไขในการสร้างเอกสารที่แตกต่างจากการลบเอกสาร หรือคุณอาจต้องการอนุญาตให้อ่านเอกสารเดียวแต่ปฏิเสธการสืบค้นจำนวนมาก
กฎ read
สามารถแบ่งออกเป็น get
และ list
ในขณะที่กฎ write
สามารถแบ่งออกเป็น create
, update
และ 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>;
}
}
}
ข้อมูลแบบลำดับชั้น
ข้อมูลใน 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>;
}
}
}
ไวด์การ์ดแบบเรียกซ้ำ
หากคุณต้องการให้กฎมีผลกับลำดับชั้นเชิงลึกที่กำหนดเอง ให้ใช้ไวยากรณ์ไวด์การ์ดแบบเรียกซ้ำ {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 โปรดดู การรักษาความปลอดภัยการสืบค้นกลุ่มคอลเลกชัน
คำสั่งการจับคู่ที่ทับซ้อนกัน
เป็นไปได้ที่เอกสารจะตรงกับคำสั่ง 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 or subcollections.
match /cities/{document=**} {
allow read, write: if true;
}
}
}
ในตัวอย่างข้างต้น การอ่านและเขียนทั้งหมดไปยังคอลเลกชัน cities
จะได้รับอนุญาต เนื่องจากกฎข้อที่สองเป็น true
เสมอ แม้ว่ากฎข้อแรกจะเป็น false
เสมอก็ตาม
ข้อจำกัดของกฎความปลอดภัย
เมื่อคุณทำงานกับกฎความปลอดภัย โปรดสังเกตข้อจำกัดต่อไปนี้:
ขีดจำกัด | รายละเอียด |
---|---|
จำนวน exists() , get() และ getAfter() สูงสุดต่อการร้องขอ |
เกินขีดจำกัดอย่างใดอย่างหนึ่งส่งผลให้เกิดข้อผิดพลาดในการปฏิเสธสิทธิ์ การเรียกเข้าถึงเอกสารบางรายการอาจถูกแคช และการเรียกที่แคชไว้จะไม่นับรวมในขีดจำกัด |
ความลึกของคำสั่งจับ match แบบซ้อนสูงสุด | 10 |
ความยาวเส้นทางสูงสุดในส่วนของเส้นทาง ได้รับอนุญาตภายในชุดคำสั่งการ match ที่ซ้อนกัน | 100 |
จำนวนตัวแปรการจับเส้นทางสูงสุดที่อนุญาตภายในชุดคำสั่งการ match แบบซ้อน | 20 |
ความลึกของการเรียกใช้ฟังก์ชันสูงสุด | 20 |
จำนวนอาร์กิวเมนต์ฟังก์ชันสูงสุด | 7 |
จำนวนสูงสุดของการเชื่อมโยงตัวแปร let ต่อฟังก์ชัน | 10 |
จำนวนสูงสุดของการเรียกใช้ฟังก์ชันแบบเรียกซ้ำหรือแบบวนรอบ | 0 (ไม่ได้รับอนุญาต) |
จำนวนนิพจน์สูงสุดที่ได้รับการประเมินต่อคำขอ | 1,000 |
ขนาดสูงสุดของชุดกฎ | ชุดกฎต้องเป็นไปตามขีดจำกัดขนาด 2 ประการ:
|