Script Valley
MongoDB: Complete Course
CRUD OperationsLesson 2.4

How to delete documents in MongoDB safely

deleteOne, deleteMany, drop vs deleteMany, soft delete pattern, findOneAndDelete, write concern basics

deleteOne and deleteMany

deleteOne vs deleteMany

deleteOne removes the first document that matches the filter and returns an object with a deletedCount of 0 or 1. deleteMany removes every matching document and returns the total count. Use a precise filter when calling these — a typo in an empty filter could delete your entire collection.

// deleteOne — removes the first match only
const r1 = await db.collection('sessions')
  .deleteOne({ token: 'abc123xyz' })
console.log(r1.deletedCount) // 0 or 1

// deleteMany — removes every match
const r2 = await db.collection('logs').deleteMany({
  createdAt: { $lt: new Date('2023-01-01') }
})
console.log(r2.deletedCount) // number of removed docs

// findOneAndDelete — atomically find, return, and delete
const job = await db.collection('queue').findOneAndDelete(
  { status: 'pending' },
  { sort: { priority: -1 } }  // highest priority first
)
console.log(job.value)  // the document that was deleted

drop vs deleteMany for clearing collections

Use collection.drop() to remove an entire collection including all its indexes in one fast operation. deleteMany({}) removes all documents but preserves the collection structure, indexes, and metadata. On large collections, drop() is orders of magnitude faster than scanning and deleting every document individually.

Soft delete pattern

// Instead of hard delete, flag and filter
await db.collection('users').updateOne(
  { _id: userId },
  { $set: { deletedAt: new Date(), isDeleted: true } }
)
// All queries must include: { isDeleted: { $ne: true } }

Up next

MongoDB query operators complete reference: $in, $exists, $regex and more

Sign in to track progress