Xoá dữ liệu bằng Hàm đám mây có thể gọi

Trang này mô tả cách sử dụng một Hàm đám mây có thể gọi để xoá dữ liệu. Sau khi triển khai chức năng này, bạn có thể gọi trực tiếp từ ứng dụng dành cho thiết bị di động hoặc trang web đến xoá đệ quy các tài liệu và bộ sưu tập. Ví dụ: bạn có thể sử dụng để cung cấp cho người dùng một số khả năng xoá toàn bộ tập hợp.

Để biết những cách khác để xoá bộ sưu tập, hãy xem phần Xoá dữ liệu.

Giải pháp: Xoá dữ liệu bằng Hàm đám mây có thể gọi

Bạn có thể gặp khó khăn khi xoá toàn bộ bộ sưu tập khỏi một ứng dụng di động có giới hạn về tài nguyên vì những lý do sau:

  • Không có thao tác nào có thể xoá từng bộ sưu tập.
  • Khi bạn xoá một tài liệu, những tài liệu trong các tập hợp con của tài liệu đó sẽ không bị xoá.
  • Nếu tài liệu của bạn có các tập hợp con động, thì bạn khó có thể biết được tập hợp con nào dữ liệu cần xoá cho một đường dẫn cụ thể.
  • Để xóa một bộ sưu tập gồm hơn 500 tài liệu, bạn phải thực hiện nhiều thao tác ghi hàng loạt hoặc hàng trăm thao tác xoá đơn lẻ.
  • Trong nhiều ứng dụng, việc cấp quyền xoá cho người dùng cuối là không phù hợp toàn bộ bộ sưu tập.

Rất may là bạn có thể viết một Hàm đám mây có thể gọi để chạy các thao tác xoá an toàn và hiệu quả đối với toàn bộ bộ sưu tập hoặc cây bộ sưu tập. Hàm đám mây ở bên dưới triển khai một hàm có thể gọi có nghĩa là họ có thể gọi trực tiếp từ ứng dụng di động hoặc trang web của bạn cho một hàm cục bộ.

Để triển khai hàm và dùng thử bản minh hoạ, hãy xem mã mẫu.

Chức năng đám mây

Hàm đám mây dưới đây sẽ xoá một tập hợp và tất cả các thành phần con.

Thay vì triển khai logic xoá đệ quy của riêng bạn cho Hàm đám mây, bạn có thể tận dụng lệnh firestore:delete trong Giao diện dòng lệnh Firebase (CLI). Bạn có thể nhập bất kỳ hàm nào của Firebase CLI vào ứng dụng Node.js bằng cách sử dụng gói firebase-tools.

Firebase CLI sử dụng Cloud Firestore REST API để tìm tất cả tài liệu theo đường dẫn được chỉ định và xoá riêng từng tài liệu. Phương thức triển khai này không yêu cầu bạn phải biết về hệ phân cấp dữ liệu cụ thể của ứng dụng và thậm chí sẽ tìm và xoá các tệp "mất nguồn gốc" tài liệu không còn có cha mẹ.

Node.js

/**
 * Initiate a recursive delete of documents at a given path.
 * 
 * The calling user must be authenticated and have the custom "admin" attribute
 * set to true on the auth token.
 * 
 * This delete is NOT an atomic operation and it's possible
 * that it may fail after only deleting some documents.
 * 
 * @param {string} data.path the document or collection path to delete.
 */
exports.recursiveDelete = functions
  .runWith({
    timeoutSeconds: 540,
    memory: '2GB'
  })
  .https.onCall(async (data, context) => {
    // Only allow admin users to execute this function.
    if (!(context.auth && context.auth.token && context.auth.token.admin)) {
      throw new functions.https.HttpsError(
        'permission-denied',
        'Must be an administrative user to initiate delete.'
      );
    }

    const path = data.path;
    console.log(
      `User ${context.auth.uid} has requested to delete path ${path}`
    );

    // Run a recursive delete on the given document or collection path.
    // The 'token' must be set in the functions config, and can be generated
    // at the command line by running 'firebase login:ci'.
    await firebase_tools.firestore
      .delete(path, {
        project: process.env.GCLOUD_PROJECT,
        recursive: true,
        force: true,
        token: functions.config().fb.token
      });

    return {
      path: path 
    };
  });

Lời gọi khách hàng

Để gọi hàm này, hãy tham chiếu đến hàm từ SDK Firebase và truyền các tham số bắt buộc:

Web
/**
 * Call the 'recursiveDelete' callable function with a path to initiate
 * a server-side delete.
 */
function deleteAtPath(path) {
    var deleteFn = firebase.functions().httpsCallable('recursiveDelete');
    deleteFn({ path: path })
        .then(function(result) {
            logMessage('Delete success: ' + JSON.stringify(result));
        })
        .catch(function(err) {
            logMessage('Delete failed, see console,');
            console.warn(err);
        });
}
Swift
Lưu ý: Sản phẩm này không hoạt động trên các mục tiêu watchOS và App Clip.
    // Snippet not yet written
    
Objective-C
Lưu ý: Sản phẩm này không hoạt động trên các mục tiêu watchOS và App Clip.
    // Snippet not yet written
    

Kotlin+KTX

/**
 * Call the 'recursiveDelete' callable function with a path to initiate
 * a server-side delete.
 */
fun deleteAtPath(path: String) {
    val deleteFn = Firebase.functions.getHttpsCallable("recursiveDelete")
    deleteFn.call(hashMapOf("path" to path))
        .addOnSuccessListener {
            // Delete Success
            // ...
        }
        .addOnFailureListener {
            // Delete Failed
            // ...
        }
}

Java

/**
 * Call the 'recursiveDelete' callable function with a path to initiate
 * a server-side delete.
 */
public void deleteAtPath(String path) {
    Map<String, Object> data = new HashMap<>();
    data.put("path", path);

    HttpsCallableReference deleteFn =
            FirebaseFunctions.getInstance().getHttpsCallable("recursiveDelete");
    deleteFn.call(data)
            .addOnSuccessListener(new OnSuccessListener<HttpsCallableResult>() {
                @Override
                public void onSuccess(HttpsCallableResult httpsCallableResult) {
                    // Delete Success
                    // ...
                }
            })
            .addOnFailureListener(new OnFailureListener() {
                @Override
                public void onFailure(@NonNull Exception e) {
                    // Delete failed
                    // ...
                }
            });
}

Bằng cách sử dụng SDK ứng dụng cho các chức năng đám mây có thể gọi, quá trình xác thực người dùng trạng thái và tham số path được truyền liền mạch đến hàm từ xa. Khi hàm hoàn tất, ứng dụng sẽ nhận được lệnh gọi lại có kết quả hoặc ngoại lệ. Để tìm hiểu về cách gọi một hàm đám mây từ Android, Apple hoặc một nền tảng khác, hãy đọc tài liệu này.

Các điểm hạn chế

Giải pháp ở trên minh hoạ việc xoá các tập hợp khỏi một lệnh gọi được nhưng bạn cần lưu ý những hạn chế sau:

  • Tính nhất quán – mã ở trên sẽ xoá từng tài liệu một. Nếu bạn trong khi vẫn đang diễn ra hoạt động xoá, kết quả của bạn có thể phản ánh trạng thái hoàn chỉnh một phần trong đó chỉ có một số tài liệu được nhắm mục tiêu bị xóa. Chúng tôi cũng không đảm bảo rằng các thao tác xoá sẽ thành công hoặc đều không thành công, vì vậy, hãy chuẩn bị để xử lý trường hợp xoá một phần.
  • Hết thời gian chờ – hàm ở trên được định cấu hình để chạy tối đa 540 giây trước khi hết thời gian chờ. Mã xoá có thể xoá 4000 tài liệu mỗi giây trong trường hợp tốt nhất. Nếu bạn cần xoá nhiều hơn 2.000.000 tài liệu, bạn nên cân nhắc tự chạy thao tác này để máy chủ không hết thời gian chờ. Ví dụ về cách xoá bộ sưu tập từ máy chủ của riêng bạn, hãy xem Xóa bộ sưu tập.