Catch up on everything announced at Firebase Summit, and learn how Firebase can help you accelerate app development and run your app with confidence. Learn More

ทริกเกอร์ Cloud Firestore

จัดทุกอย่างให้เป็นระเบียบอยู่เสมอด้วยคอลเล็กชัน บันทึกและจัดหมวดหมู่เนื้อหาตามค่ากำหนดของคุณ

ด้วย Cloud Functions คุณสามารถจัดการเหตุการณ์ใน Cloud Firestore โดยไม่จำเป็นต้องอัปเดตรหัสไคลเอนต์ คุณสามารถทำการเปลี่ยนแปลง Cloud Firestore ผ่านอินเทอร์เฟซ DocumentSnapshot หรือผ่าน Admin SDK

ในวงจรชีวิตทั่วไป ฟังก์ชัน Cloud Firestore จะทำสิ่งต่อไปนี้:

  1. รอการเปลี่ยนแปลงในเอกสารเฉพาะ
  2. ทริกเกอร์เมื่อมีเหตุการณ์เกิดขึ้นและดำเนินการตามงานต่างๆ (ดูตัวอย่างกรณีการใช้งาน ฉันทำอะไรได้บ้างกับ Cloud Functions )
  3. รับวัตถุข้อมูลที่มีภาพรวมของข้อมูลที่จัดเก็บไว้ในเอกสารที่ระบุ สำหรับเหตุการณ์ onWrite หรือ onUpdate ออบเจ็กต์ข้อมูลจะมีสแน็ปช็อตสองภาพที่แสดงสถานะข้อมูลก่อนและหลังเหตุการณ์ทริกเกอร์

ระยะทางระหว่างตำแหน่งของอินสแตนซ์ Firestore และตำแหน่งของฟังก์ชันสามารถสร้างเวลาแฝงของเครือข่ายได้อย่างมีนัยสำคัญ เพื่อเพิ่มประสิทธิภาพ ให้พิจารณาระบุตำแหน่ง ฟังก์ชัน ที่เกี่ยวข้อง

ทริกเกอร์ฟังก์ชัน Cloud Firestore

Cloud Functions สำหรับ Firebase SDK ส่งออกวัตถุ functions.firestore ที่ช่วยให้คุณสร้างตัวจัดการที่เชื่อมโยงกับเหตุการณ์ Cloud Firestore เฉพาะ

ประเภทเหตุการณ์ สิ่งกระตุ้น
onCreate ทริกเกอร์เมื่อมีการเขียนเอกสารเป็นครั้งแรก
onUpdate ทริกเกอร์เมื่อมีเอกสารอยู่แล้วและมีการเปลี่ยนแปลงค่าใดๆ
onDelete ทริกเกอร์เมื่อเอกสารที่มีข้อมูลถูกลบ
onWrite ทริกเกอร์เมื่อ onCreate , onUpdate หรือ onDelete ถูกทริกเกอร์

หากคุณยังไม่ได้เปิดใช้โปรเจ็กต์สำหรับ Cloud Functions for Firebase ให้อ่าน เริ่มต้นใช้งาน: เขียนและปรับใช้ฟังก์ชันแรกของคุณ เพื่อกำหนดค่าและตั้งค่าโปรเจ็กต์ Cloud Functions สำหรับ Firebase

การเขียนฟังก์ชันที่ทริกเกอร์ Cloud Firestore

กำหนดทริกเกอร์ฟังก์ชัน

หากต้องการกำหนดทริกเกอร์ Cloud Firestore ให้ระบุเส้นทางเอกสารและประเภทเหตุการณ์:

โหนด js

const functions = require('firebase-functions');

exports.myFunction = functions.firestore
  .document('my-collection/{docId}')
  .onWrite((change, context) => { /* ... */ });

เส้นทางเอกสารสามารถอ้างอิง เอกสารเฉพาะ หรือ รูปแบบตัวแทน

ระบุเอกสารเดียว

หากคุณต้องการทริกเกอร์เหตุการณ์สำหรับการเปลี่ยนแปลง ใดๆ ในเอกสารเฉพาะ คุณสามารถใช้ฟังก์ชันต่อไปนี้ได้

โหนด js

// Listen for any change on document `marie` in collection `users`
exports.myFunctionName = functions.firestore
    .document('users/marie').onWrite((change, context) => {
      // ... Your code here
    });

ระบุกลุ่มของเอกสารโดยใช้สัญลักษณ์แทน

หากคุณต้องการแนบทริกเกอร์กับกลุ่มของเอกสาร เช่น เอกสารใดๆ ในคอลเลกชั่นหนึ่งๆ ให้ใช้ {wildcard} ID ของเอกสาร:

โหนด js

// Listen for changes in all documents in the 'users' collection
exports.useWildcard = functions.firestore
    .document('users/{userId}')
    .onWrite((change, context) => {
      // If we set `/users/marie` to {name: "Marie"} then
      // context.params.userId == "marie"
      // ... and ...
      // change.after.data() == {name: "Marie"}
    });

ในตัวอย่างนี้ เมื่อฟิลด์ใดๆ ในเอกสารใดๆ ใน users มีการเปลี่ยนแปลง ฟิลด์นั้นจะจับคู่กับไวด์การ์ดที่เรียกว่า userId

หากเอกสารใน users มีคอลเล็กชันย่อย และฟิลด์ในหนึ่งในเอกสารของคอลเล็กชันย่อยเหล่านั้นมีการเปลี่ยนแปลง ไวลด์การ์ด userId จะ ไม่ ทำงาน

การจับคู่สัญลักษณ์ตัวแทนจะถูกแยกออกจากเส้นทางเอกสารและจัดเก็บไว้ใน context.params คุณสามารถกำหนดสัญลักษณ์แทนได้มากเท่าที่คุณต้องการเพื่อแทนที่คอลเล็กชันหรือ ID เอกสารที่ชัดเจน ตัวอย่างเช่น:

โหนด js

// Listen for changes in all documents in the 'users' collection and all subcollections
exports.useMultipleWildcards = functions.firestore
    .document('users/{userId}/{messageCollectionId}/{messageId}')
    .onWrite((change, context) => {
      // If we set `/users/marie/incoming_messages/134` to {body: "Hello"} then
      // context.params.userId == "marie";
      // context.params.messageCollectionId == "incoming_messages";
      // context.params.messageId == "134";
      // ... and ...
      // change.after.data() == {body: "Hello"}
    });

ทริกเกอร์เหตุการณ์

เรียกใช้ฟังก์ชันเมื่อมีการสร้างเอกสารใหม่

คุณสามารถทริกเกอร์ฟังก์ชันให้เริ่มทำงานได้ทุกเมื่อที่มีการสร้างเอกสารใหม่ในคอลเล็กชันโดยใช้ตัวจัดการ onCreate() ที่มี ไว ด์การ์ด ฟังก์ชันตัวอย่างนี้เรียกใช้ createUser ทุกครั้งที่มีการเพิ่มโปรไฟล์ผู้ใช้ใหม่:

โหนด js

exports.createUser = functions.firestore
    .document('users/{userId}')
    .onCreate((snap, context) => {
      // Get an object representing the document
      // e.g. {'name': 'Marie', 'age': 66}
      const newValue = snap.data();

      // access a particular field as you would any JS property
      const name = newValue.name;

      // perform desired operations ...
    });

เรียกใช้ฟังก์ชันเมื่อมีการอัปเดตเอกสาร

คุณยังสามารถทริกเกอร์ฟังก์ชันให้เริ่มทำงานเมื่อมีการอัปเดตเอกสารโดยใช้ onUpdate() ที่มี ไว ด์การ์ด ฟังก์ชันตัวอย่างนี้เรียกใช้ updateUser หากผู้ใช้เปลี่ยนโปรไฟล์:

โหนด js

exports.updateUser = functions.firestore
    .document('users/{userId}')
    .onUpdate((change, context) => {
      // Get an object representing the document
      // e.g. {'name': 'Marie', 'age': 66}
      const newValue = change.after.data();

      // ...or the previous value before this update
      const previousValue = change.before.data();

      // access a particular field as you would any JS property
      const name = newValue.name;

      // perform desired operations ...
    });

เรียกใช้ฟังก์ชันเมื่อเอกสารถูกลบ

คุณยังสามารถทริกเกอร์ฟังก์ชันเมื่อเอกสารถูกลบโดยใช้ onDelete() ที่มี ไว ด์การ์ด ฟังก์ชันตัวอย่างนี้เรียกใช้ deleteUser เมื่อผู้ใช้ลบโปรไฟล์ผู้ใช้ของตน:

โหนด js

exports.deleteUser = functions.firestore
    .document('users/{userID}')
    .onDelete((snap, context) => {
      // Get an object representing the document prior to deletion
      // e.g. {'name': 'Marie', 'age': 66}
      const deletedValue = snap.data();

      // perform desired operations ...
    });

ทริกเกอร์ฟังก์ชันสำหรับการเปลี่ยนแปลงทั้งหมดในเอกสาร

หากคุณไม่สนใจเกี่ยวกับประเภทของเหตุการณ์ที่เริ่มทำงาน คุณสามารถฟังการเปลี่ยนแปลงทั้งหมดในเอกสาร Cloud Firestore โดยใช้ onWrite() ที่มี ไว ด์การ์ด ฟังก์ชันตัวอย่างนี้เรียกใช้ modifyUser ถ้าผู้ใช้ถูกสร้าง อัปเดต หรือลบ:

โหนด js

exports.modifyUser = functions.firestore
    .document('users/{userID}')
    .onWrite((change, context) => {
      // Get an object with the current document value.
      // If the document does not exist, it has been deleted.
      const document = change.after.exists ? change.after.data() : null;

      // Get an object with the previous document value (for update or delete)
      const oldDocument = change.before.data();

      // perform desired operations ...
    });

การอ่านและการเขียนข้อมูล

เมื่อมีการทริกเกอร์ฟังก์ชัน ฟังก์ชันจะแสดงสแนปชอตของข้อมูลที่เกี่ยวข้องกับเหตุการณ์ คุณสามารถใช้สแนปชอตนี้เพื่ออ่านหรือเขียนไปยังเอกสารที่ทำให้เกิดเหตุการณ์ หรือใช้ Firebase Admin SDK เพื่อเข้าถึงส่วนอื่นๆ ของฐานข้อมูล

ข้อมูลเหตุการณ์

การอ่านข้อมูล

เมื่อเรียกใช้ฟังก์ชัน คุณอาจต้องการรับข้อมูลจากเอกสารที่อัปเดตแล้ว หรือรับข้อมูลก่อนอัปเดต คุณสามารถรับข้อมูลก่อนหน้าได้โดยใช้ change.before.data() ซึ่งมีภาพรวมของเอกสารก่อนการอัปเดต ในทำนองเดียวกัน change.after.data() มีสถานะภาพรวมของเอกสารหลังจากการอัพเดต

โหนด js

exports.updateUser2 = functions.firestore
    .document('users/{userId}')
    .onUpdate((change, context) => {
      // Get an object representing the current document
      const newValue = change.after.data();

      // ...or the previous value before this update
      const previousValue = change.before.data();
    });

คุณสามารถเข้าถึงคุณสมบัติได้เช่นเดียวกับที่คุณทำในวัตถุอื่นๆ หรือคุณสามารถใช้ฟังก์ชัน get เพื่อเข้าถึงฟิลด์เฉพาะได้:

โหนด js

// Fetch data using standard accessors
const age = snap.data().age;
const name = snap.data()['name'];

// Fetch data using built in accessor
const experience = snap.get('experience');

การเขียนข้อมูล

การเรียกใช้ฟังก์ชันแต่ละรายการเชื่อมโยงกับเอกสารเฉพาะในฐานข้อมูล Cloud Firestore ของคุณ คุณสามารถเข้าถึงเอกสารนั้นเป็น DocumentReference ในคุณสมบัติ ref ของสแน็ปช็อตที่ส่งคืนไปยังฟังก์ชันของคุณ

DocumentReference นี้มาจาก Cloud Firestore Node.js SDK และมีเมธอดต่างๆ เช่น update() , set() และ remove() เพื่อให้คุณสามารถแก้ไขเอกสารที่ทริกเกอร์ฟังก์ชันได้อย่างง่ายดาย

โหนด js

// Listen for updates to any `user` document.
exports.countNameChanges = functions.firestore
    .document('users/{userId}')
    .onUpdate((change, context) => {
      // Retrieve the current and previous value
      const data = change.after.data();
      const previousData = change.before.data();

      // We'll only update if the name has changed.
      // This is crucial to prevent infinite loops.
      if (data.name == previousData.name) {
        return null;
      }

      // Retrieve the current count of name changes
      let count = data.name_change_count;
      if (!count) {
        count = 0;
      }

      // Then return a promise of a set operation to update the count
      return change.after.ref.set({
        name_change_count: count + 1
      }, {merge: true});
    });

ข้อมูลที่อยู่นอกเหตุการณ์ทริกเกอร์

Cloud Functions ดำเนินการในสภาพแวดล้อมที่เชื่อถือได้ ซึ่งหมายความว่าได้รับอนุญาตเป็นบัญชีบริการในโครงการของคุณ คุณสามารถอ่านและเขียนโดยใช้ Firebase Admin SDK :

โหนด js

const admin = require('firebase-admin');
admin.initializeApp();

const db = admin.firestore();

exports.writeToFirestore = functions.firestore
  .document('some/doc')
  .onWrite((change, context) => {
    db.doc('some/otherdoc').set({ ... });
  });

ข้อจำกัด

โปรดสังเกตข้อจำกัดต่อไปนี้สำหรับทริกเกอร์ Cloud Firestore สำหรับ Cloud Functions:

  • ไม่รับประกันการสั่งซื้อ การเปลี่ยนแปลงอย่างรวดเร็วสามารถทริกเกอร์การเรียกใช้ฟังก์ชันในลำดับที่ไม่คาดคิด
  • มีการส่งเหตุการณ์อย่างน้อยหนึ่งครั้ง แต่เหตุการณ์เดียวอาจส่งผลให้เกิดการเรียกใช้ฟังก์ชันหลายรายการ หลีกเลี่ยงการขึ้นอยู่กับกลไกเพียงครั้งเดียว และเขียน ฟังก์ชัน idempotent
  • ทริกเกอร์ Cloud Firestore สำหรับ Cloud Functions ใช้ได้เฉพาะกับ Cloud Firestore ในโหมด เนทีฟ ไม่พร้อมใช้งานสำหรับ Cloud Firestore ในโหมด Datastore