Delete Firebase Storage Folder on Delete of a Firestore Document

Delete Firebase Storage Folder on Delete of a Firestore Document

There are times when we want to offload certain operations from our app to a background process to better improve the user experience of the app. Typically, this would be operations that are time consuming and are required to be done in real-time. For example, image transformations or deleting image folder in the background process.

Both of the above use cases are good examples for leveraging Firebase Functions. In this post we will look at how we can use a Firebase function that runs as below

Trigger:

  • On delete of a Firestore database document

Actions:

  • Identify the unique Firebase storage folder(virtual path) that needs to be deleted using the information from the document path on which the function is triggered.
  • Access the storage account associated with the app in the function and delete the target folder.

Let's look at it with an example using the below use case in my app.

Use case: My app has a record called Location that is basically a Firebase document. When the user deletes the location document we want to delete the photos associated with the location.

Firestore document path : users/{userId}/locations/{locationId}

Document path that out function listens for delete event to trigger the execution.

Storage folder path: users/{userId}/locations/{locationId}

The virtual folder path that contains all the photos associated with the location record. This follows the same pattern as the document. You might have a different path but as long as you can build the unique path in your function, that's all that matters.

Now, let's look at the actual function that performs the deletion.

There are 3 main things that need to be done for the deletion

  1. Import the Firebase admin module provide by the Firebase SDK to access the storage service.
  2. Initialize the storage bucket of the app. At this point the bucket references the path to the root of the app.
  3. Make sure to set the prefix to unique folder that you want to delete associated with the record. This is very important, missing this prefix could delete the contents of the storage bucket.

Here is the actual code, if you want a quick way to tweak it to your needs

import * as functions from "firebase-functions";
import * as admin from "firebase-admin";

const bucketName = "yourappname.appspot.com";

//Function that triggers on delete of a Location document to 
//delete the storage bucket associated with the location
exports.deleteLocation = functions.firestore
    .document("users/{userId}/locations/{locationId}")
    .onDelete((snap, context) => {
        const { userId, locationId } = context.params;

        console.log(`Bucket : ${bucketName}`);

        const folder = `users/${userId}/locations/${locationId}`;
        //Note typically the bucket name is not needed, and you can skip             //specifying the bucket name as parameter below
        const bucket = admin.storage().bucket(bucketName);

        async function deleteBucket() {
            console.log(`Folder ${folder} delete initiated`);
            await bucket.deleteFiles({ prefix: folder });

            console.log(`Folder ${folder}  deleted`);
        }

        console.log(`Requesting delete of folder: ${folder}`);
        deleteBucket().catch((err) => {
            console.error(`Error occurred while deleting the folder: ${folder}`, err);
        });

    });

Hope this helps you to configure your Firebase cloud function to perform the deletion of a Firebase storage folder.

Feel free to post any questions or comments below if you experience any issues. Have a great day!