Home > Net >  Mongoose: How to trigger a function after a delete event is called using TTL
Mongoose: How to trigger a function after a delete event is called using TTL

Time:06-18

I am learing MongoDb and doing a project by using Mongoose on a Node js server. I have a collection "Venue". I am trying to implement softDelete for my Venues. By doing so a user can delete a Venue which can be recovered within 15 days else it will be delete because of TTL trigger. To achieve this I am using a boolean variable "softDeleted" and have created an index on "expireAt" field. When the venue is softdeleted, the variable softDeleted is set to true and the TTL is triggered.

module.exports.softDeleteVenue = async (req, res) => {
  console.log('/softDeleteVenue/:id')
  try {
    const venue = await Venue.findById(req.params.id)
    venue.softDelete = true
    venue.expireAt = moment().add(15, 'days')
    await venue.save()
    res.json({
      status: 'success',
      message: 'Venue temporarily deleted successfully',
    })
  } catch (err) {
    console.log(err)
    res.json({ status: 'error', error: err })
  }
}

The venue has a field "images" which contains URL of images on a storage(can be either cloud or local). I want to delete all the images related to the venue once the Venue is deleted. I am unable to do this when i am softDeleting Venues.

const VenueSchema = Schema({
  venueOwnerID: {
    type: Schema.Types.ObjectId,
    ref: 'User',
  },
  venueName: {
    type: String,
    required: [true, "Please Provide Venue Name"],
    // unique: true,
  },
  venueCapacity: {
    type: Number,
    required: true,
    default: 0,
  },
  contactPhone: {
    type: String,
    required: [true, "Please Provide Venue Contact Phone"],
  },
  images: [{
    type: String,        //link to images on Online or Local Storage
  }],
  videos: {
    type: String,         //link to video on Online or Local storage 
  },
  coverImageURL: {
    type: String,
  },
  createdAt: {
    type: Date,
    default: Date.now,
    required: true,
  },
  expireAt: {
    type: Date,
    default: null,
  },
  softDeleted: {
    type: Boolean,
    default: false,
  },
});

VenueSchema.index({ expireAt: 1 }, { expireAfterSeconds: 0 })

const Venue = mongoose.model('Venue', VenueSchema)

Is there a way to call a function for deleting the images once the event to delete the document is triggered.

CodePudding user response:

TTL deletions are handled by MongoDB. You could connect to a Change stream for that and listen for the deletes. But what about deletes that happen when your app does not run?

A more robust approach would be to store the urls to be deleted in a collection when the soft delete happens along with the date when to delete the images. A job checks this collection on a daily basis and purges the images.

A bit simpler yet more resource intensive would be to enumerate the images in a job on a daily basis and check whether there are still references in the venues collection. If not, the image can be removed.

  • Related